不要怂,就是干,撸起袖子干!

Commit b75a6c29 by Jan Aagaard Meier

Moved docs to main repo

1 parent 78cf2b4a
......@@ -9,5 +9,3 @@ test/binary/tmp/*
test/tmp/*
test/sqlite/test.sqlite
coverage-*
docs/*.md
docs/*.html
\ No newline at end of file
# Documentation
The sequelize documentation is written in a combination of markdown (articles and example based documentation) and [JSDoc](http://usejsdoc.org) (API reference generated from source code comments).
All documentation is located in `docs` folder.
The documentation is rendered using [mkdocs](http://mkdocs.org) and hosted at [Read the docs](http://sequelize.readthedocs.org). Mkdocs generates static HTML from markdown files. The files in `articles` and `docs` should be edited directly, and the files in `api` are generated from source code comments (more on that later).
All pages in the documentation are defined in `mkdocs.yml`, in the `pages` section. Each page is given as a separate line:
```yml
- ['index.md', 'Home', 'Welcome']
```
The first array element is the path of the markdown file, relative to the `docs` dir. The second element is the section the page should be placed in, and the third is the name of the page.
To view the docs locally use `mkdocs serve`. This will start a local server at port 8000. The documentation is automatically regenerated when you edit an `.md` file. However, you'll have to restart the server if you add new pages in the configuration file.
## Articles and example based docs
Write markdown, and have fun :)
## API docs
The API documentation is generated from source code comments by a custom script, which outputs markdown into the `docs/api` folder. To regenerate the documentation, run
```bash
$ npm run docs
```
By default all generation will be regenerated, but you can run the generation for a single file by specifying `--file`.
......@@ -90,9 +90,3 @@ coveralls: sqlite-cover mysql-cover postgres-cover postgres-native-cover mariadb
codeclimate: sqlite-cover mysql-cover postgres-cover postgres-native-cover mariadb-cover merge-coverage codeclimate-send
.PHONY: sqlite mysql postgres pgsql postgres-native postgresn all test
api-docs:
node docs/docs-generator.js
clean:
node docs/docs-generator.js --clean
<a name="datatypes"></a>
# Class DataTypes
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L309)
A convenience class holding commonly used data types. The datatypes are used when definining a new model using `Sequelize.define`, like this:
```js
sequelize.define('model', {
column: DataTypes.INTEGER
})
```
When defining a model you can just as easily pass a string as type, but often using the types defined here is beneficial. For example, using `DataTypes.BLOB`, mean
that that column will be returned as an instance of `Buffer` when being fetched by sequelize.
Some data types have special properties that can be accessed in order to change the data type. For example, to get an unsigned integer with zerofill you can do `DataTypes.INTEGER.UNSIGNED.ZEROFILL`.
The order you access the properties in do not matter, so `DataTypes.INTEGER.ZEROFILL.UNSIGNED` is fine as well. The available properties are listed under each data type.
To provide a length for the data type, you can invoke it like a function: `INTEGER(2)`
Three of the values provided here (`NOW`, `UUIDV1` and `UUIDV4`) are special default values, that should not be used to define types. Instead they are used as shorthands for
defining default values. For example, to get a uuid field with a default value generated following v1 of the UUID standard:
```js
sequelize.define('model', {
uuid: {
type: DataTypes.UUID,
defaultValue: DataTypes.UUIDV1,
primaryKey: true
}
})
```
***
<a name="string"></a>
## `STRING`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L317)
A variable length string. Default length 255
Available properties: `BINARY`
***
<a name="char"></a>
## `CHAR`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L325)
A fixed length string. Default length 255
Available properties: `BINARY`
***
<a name="text"></a>
## `TEXT`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L330)
An unlimited length text column
***
<a name="integer"></a>
## `INTEGER`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L338)
A 32 bit integer.
Available properties: `UNSIGNED`, `ZEROFILL`
***
<a name="bigint"></a>
## `BIGINT`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L346)
A 64 bit integer.
Available properties: `UNSIGNED`, `ZEROFILL`
***
<a name="date"></a>
## `DATE`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L351)
A datetime column
***
<a name="dateonly"></a>
## `DATEONLY`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L356)
A date only column
***
<a name="boolean"></a>
## `BOOLEAN`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L361)
A boolean / tinyint column, depending on dialect
***
<a name="float"></a>
## `FLOAT`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L369)
Floating point number. Accepts one or two arguments for precision
Available properties: `UNSIGNED`, `ZEROFILL`
***
<a name="now"></a>
## `NOW`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L374)
A default value of the current timestamp
***
<a name="blob"></a>
## `BLOB`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L380)
Binary storage. Available lengths: `tiny`, `medium`, `long`
***
<a name="decimal"></a>
## `DECIMAL`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L388)
Decimal number. Accepts one or two arguments for precision
Available properties: `UNSIGNED`, `ZEROFILL`
***
<a name="uuid"></a>
## `UUID`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L393)
A column storing a unique univeral identifier. Use with `UUIDV1` or `UUIDV4` for default values.
***
<a name="uuidv1"></a>
## `UUIDV1`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L398)
A default unique universal identifier generated following the UUID v1 standard
***
<a name="uuidv4"></a>
## `UUIDV4`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L403)
A default unique universal identifier generated following the UUID v2 standard
***
<a name="hstore"></a>
## `HSTORE`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L409)
A key / value column. Only available in postgres.
***
<a name="virtual"></a>
## `VIRTUAL`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L449)
A virtual value that is not stored in the DB. This could for example be useful if you want to provide a default value in your model
that is returned to the user but not stored in the DB.
You could also use it to validate a value before permuting and storing it. Checking password length before hashing it for example:
```js
sequelize.define('user', {
password_hash: DataTypes.STRING
password: {
type: DataTypes.VIRTUAL,
set: function (val) {
this.setDataValue('password', val);
this.setDataValue('password_hash', this.salt + val);
},
validate: {
isLongEnough: function (val) {
if (val.length < 7) {
throw new Error("Please choose a longer password")
}
}
}
}
})
```
In the above code the password is stored plainly in the password field so it can be validated, but is never stored in the DB.
__Aliases:__ NONE
***
<a name="enum"></a>
## `ENUM`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L457)
An enumeration. `DataTypes.ENUM('value', 'another value')`.
***
<a name="array"></a>
## `ARRAY()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/data-types.js#L477)
An array of `type`, e.g. `DataTypes.ARRAY(DataTypes.DECIMAL)`. Only available in postgres.
***
_This document is automatically generated based on source code comments. Please do not edit it directly, as your changes will be ignored. Please write on <a href="irc://irc.freenode.net/#sequelizejs">IRC</a>, open an issue or a create a pull request if you feel something can be improved. For help on how to write source code documentation see [JSDoc](http://usejsdoc.org) and [dox](https://github.com/tj/dox)_
\ No newline at end of file
<a name="errors"></a>
# Class Errors
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L11)
Sequelize provides a host of custom error classes, to allow you to do easier debugging. All of these errors are exposed on the sequelize object and the sequelize constructor.
All sequelize errors inherit from the base JS error object.
***
<a name="baseerror"></a>
## `new BaseError()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L20)
The Base Error all Sequelize Errors inherit from.
__Aliases:__ Error
***
<a name="validationerror"></a>
## `new ValidationError(message, [errors])`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L40)
Validation Error. Thrown when the sequelize validation has failed. The error contains an `errors` property,
which is an array with 1 or more ValidationErrorItems, one for each validation that failed.
**Params:**
| Name | Type | Description |
| ---- | ---- | ----------- |
| message | string | Error message |
| [errors] | Array | Array of ValidationErrorItem objects describing the validation errors |
__Extends:__ BaseError
***
<a name="get"></a>
## `get(path)`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L53)
Gets all validation error items for the path / field specified.
**Params:**
| Name | Type | Description |
| ---- | ---- | ----------- |
| path | string | The path to be checked for error items |
***
<a name="errors"></a>
## `errors()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L67)
An array of ValidationErrorItems
***
<a name="databaseerror"></a>
## `new DatabaseError()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L74)
A base class for all database related errors.
__Extends:__ BaseError
***
<a name="parent"></a>
## `parent()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L88)
The database specific error which triggered this one
***
<a name="sql"></a>
## `sql()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L94)
The SQL that triggered the error
***
<a name="timeouterror"></a>
## `new TimeoutError()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L101)
Thrown when a database query times out because of a deadlock
__Extends:__ DatabaseError
***
<a name="uniqueconstrainterror"></a>
## `new UniqueConstraintError()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L112)
Thrown when a unique constraint is violated in the database
__Extends:__ DatabaseError
***
<a name="foreignkeyconstrainterror"></a>
## `new ForeignKeyConstraintError()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L131)
Thrown when a foreign key constraint is violated in the database
__Extends:__ DatabaseError
***
<a name="message"></a>
## `message()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L151)
The message from the DB.
***
<a name="fields"></a>
## `fields()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L157)
The fields of the unique constraint
***
<a name="value"></a>
## `value()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L163)
The value(s) which triggered the error
***
<a name="index"></a>
## `index()`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L169)
The name of the index that triggered the error
***
<a name="validationerroritem"></a>
## `new ValidationErrorItem(message, type, path, value)`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/errors.js#L181)
Validation Error Item
Instances of this class are included in the `ValidationError.errors` property.
**Params:**
| Name | Type | Description |
| ---- | ---- | ----------- |
| message | string | An error message |
| type | string | The type of the validation error |
| path | string | The field that triggered the validation error |
| value | string | The value that generated the error |
***
_This document is automatically generated based on source code comments. Please do not edit it directly, as your changes will be ignored. Please write on <a href="irc://irc.freenode.net/#sequelizejs">IRC</a>, open an issue or a create a pull request if you feel something can be improved. For help on how to write source code documentation see [JSDoc](http://usejsdoc.org) and [dox](https://github.com/tj/dox)_
\ No newline at end of file
<a name="promise"></a>
# Class Promise
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/promise.js#L25)
A slightly modified version of bluebird promises. This means that, on top of the methods below, you can also call all the methods listed on the link below.
The main difference is that sequelize promises allows you to attach a listener that will be called with the generated SQL, each time a query is run.
The sequelize promise class works seamlessly with other A+/thenable libraries, with one exception.
If you want to propagate SQL events across `then`, `all` calls etc., you must use sequelize promises exclusively.
### Mixes:
* https://github.com/petkaantonov/bluebird/blob/master/API.md
***
<a name="on"></a>
## `on(evt, fct)`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/promise.js#L110)
Listen for events, event emitter style. Mostly for backwards compat. with EventEmitter
**Deprecated**
**Params:**
| Name | Type | Description |
| ---- | ---- | ----------- |
| evt | String | |
| fct | Function | |
***
<a name="emit"></a>
## `emit(type, value(s)*)`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/promise.js#L131)
Emit an event from the emitter
**Deprecated**
**Params:**
| Name | Type | Description |
| ---- | ---- | ----------- |
| type | string | The type of event |
| value(s)* | any | All other arguments will be passed to the event listeners |
***
<a name="success"></a>
## `success(onSuccess)` -> `this`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/promise.js#L169)
Listen for success events.
```js
promise.success(function (result) {
//...
});
```
**Deprecated**
**Params:**
| Name | Type | Description |
| ---- | ---- | ----------- |
| onSuccess | function | |
__Aliases:__ ok
***
<a name="error"></a>
## `error(onError)` -> `this`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/promise.js#L196)
Listen for error events
```js
promise.error(function (err) {
//...
});
```
**Deprecated**
**Params:**
| Name | Type | Description |
| ---- | ---- | ----------- |
| onError | function | |
__Aliases:__ fail, failure
***
<a name="done"></a>
## `done(onDone)` -> `this`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/promise.js#L219)
Listen for both success and error events.
```js
promise.done(function (err, result) {
//...
});
```
**Deprecated** done(fct) is deprecated, done() is regular promise syntax to explicitly signal the end of a promise chain and will not be deprecated
**Params:**
| Name | Type | Description |
| ---- | ---- | ----------- |
| onDone | function | |
__Aliases:__ complete
***
<a name="sql"></a>
## `sql(onSQL)` -> `this`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/promise.js#L244)
Attach a function that is called every time the function that created this emitter executes a query.
**Params:**
| Name | Type | Description |
| ---- | ---- | ----------- |
| onSQL | function | |
***
<a name="proxy"></a>
## `proxy(promise, [options])` -> `this`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/promise.js#L259)
Proxy every event of this promise to another one.
**Deprecated**
**Params:**
| Name | Type | Description |
| ---- | ---- | ----------- |
| promise | SequelizePromise | The promise that should receive the events. |
| [options] | Object | |
| [options.events] | Array | An array of the events to proxy. Defaults to sql, error and success |
***
_This document is automatically generated based on source code comments. Please do not edit it directly, as your changes will be ignored. Please write on <a href="irc://irc.freenode.net/#sequelizejs">IRC</a>, open an issue or a create a pull request if you feel something can be improved. For help on how to write source code documentation see [JSDoc](http://usejsdoc.org) and [dox](https://github.com/tj/dox)_
\ No newline at end of file
<a name="transaction"></a>
# Class Transaction
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/transaction.js#L12)
The transaction object is used to identify a running transaction. It is created by calling `Sequelize.transaction()`.
To run a query under a transaction, you should pass the transaction in the options object.
***
<a name="isolation_levels"></a>
## `ISOLATION_LEVELS`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/transaction.js#L45)
The possible isolations levels to use when starting a transaction
```js
{
READ_UNCOMMITTED: "READ UNCOMMITTED",
READ_COMMITTED: "READ COMMITTED",
REPEATABLE_READ: "REPEATABLE READ",
SERIALIZABLE: "SERIALIZABLE"
}
```
***
<a name="lock"></a>
## `LOCK`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/transaction.js#L67)
Possible options for row locking. Used in conjuction with `find` calls:
```js
t1 // is a transaction
Model.findAll({
where: ...
}, {
transaction: t1,
lock: t1.LOCK.UPDATE,
lock: t1.LOCK.SHARE
})
```
***
<a name="commit"></a>
## `commit()` -> `this`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/transaction.js#L77)
Commit the transaction
***
<a name="rollback"></a>
## `rollback()` -> `this`
[View code](https://github.com/sequelize/sequelize/blob/5aa77fa291abeaf0498f65724000c75da9ab9028/lib/transaction.js#L97)
Rollback (abort) the transaction
***
_This document is automatically generated based on source code comments. Please do not edit it directly, as your changes will be ignored. Please write on <a href="irc://irc.freenode.net/#sequelizejs">IRC</a>, open an issue or a create a pull request if you feel something can be improved. For help on how to write source code documentation see [JSDoc](http://usejsdoc.org) and [dox](https://github.com/tj/dox)_
\ No newline at end of file
<script type="text/javascript">
fromGithub = function (partialId, ext) {
ext = ext || '';
var $partial = $("#" + partialId)
$.get("https://cdn.rawgit.com/sequelize/express-example/master/" + partialId.replace("_", "/") + ext, function (code) {
if (ext === '.js') {
code = hljs.highlight('js', code).value;
}
code = '<div class="highlight"><pre>' + code + '</pre></div>';
$partial.replaceWith(code);
}, 'html');
}
</script>
## Introduction
This article explains the usage of Sequelize with the MVC framework Express.You will learn how and where to define models and how to load them when needed.
## A minimal express application
In order to create a minimal express application, we need to install express first and scaffold a project. We can do this via the following commands:
```bash
$ mkdir example-app
$ cd example-app
$ npm install express express-generator
$ node_modules/.bin/express . -f
$ npm install
$ ./bin/www
```
You should now be able to see a tiny welcome page on `http://localhost:3000`
## Adding Sequelize to the application
Now that we have the express application in place, we can start adding Sequelize to it. What we need for that are the following packages: sequelize, sequelize-cli, sqlite3. Please note, that for the sake of simplicity this tutorial will use SQLite.
```bash
$ npm install --save sequelize@2.0.0-rc1 sequelize-cli sqlite3
```
This will install the respective packages and uses the upcoming major release of sequelize. We can now let the sequelize CLI initialize the project's directory:
```bash
$ node_modules/.bin/sequelize init
```
Running this command will create the folders `config`, `migrations` and `models`.
## Implementing a todo app
As an example application we will create a very basic and simple todo tool, which allows the creation of users and the management of their tasks.
### bin/www
In order to create a maintainable application, we will put all the database logic into the `models` folder. When the application gets fired up, sequelize will sync the models with the database and afterwards start the server. This way we don't clutter the application while making use of sequelize's features.
<div id="bin_www"></div>
<script>$(function () { fromGithub("bin_www") })</script>
### models/index.js
This file has been generated with the sequelize CLI and collects all the models from the `models` directory and associates them if needed.
<div id="models_index"></div>
<script>$(function () { fromGithub("models_index", '.js') })</script>
### models/user.js
All models of our application are located as separate files in the `models` folder. If you want to add a new model, just add it to this folder and everything will work automagically. Also you can use the sequelize CLI's `sequelize model:create`.
**Notice** that the `associate` method receives a parameter `models`, which contains every declared model within the models directory.
<div id="models_user"></div>
<script>$(function () { fromGithub("models_user", '.js') })</script>
### models/task.js
The other needed model is `Task`. It relates to the `User`.
<div id="models_task"></div>
<script>$(function () { fromGithub("models_task", '.js') })</script>
### routes/index.js
The file `routes/index.js` contains the logic for a request against the main homepage. It loads the models module and uses it to load all the users and tasks from the database.
<div id="routes_index"></div>
<script>$(function () { fromGithub("routes_index", '.js') })</script>
This will allow us to iterate over the users in the view file. We will skip the rest of the route files for this article.
### views/index.jade
As we passed the users to the view and include the tasks for each user, we can access the data in the view's template file. Besides listing the users and tasks, there are also forms for creating new instances.
<div id="views_index"></div>
<script>$(function () { fromGithub("views_index", '.jade') })</script>
## What's next?
This article shows a basic approach of how to integrate Sequelize into an ExpressJS application. It allows the very easy management of models by adding new files to a specific folder. Starting the application will automatically sync the schema with the database.
If you don't want to have automatic schema synchronization and instead want migrations, just add a respective step to your deployment script. When you use the CLI for the model generation, you will gain the migration scripts for free as well.
You can find the complete application code [on Github](https://github.com/sequelize/express-example). Feel free to add pull requests to it.
Besides the use of Sequelize as model backend in your ExpressJS application, you might also want to turn your server into a restful API. If that is the case, check out [the repository on Github](https://github.com/sequelize/sequelize-restful)
\ No newline at end of file
## Introduction
This section covers the use of Sequelize on Heroku. It will explain how to get started with Heroku and what is necessary to setup a proper environment. We will use MySQL on the development machine and PostgreSQL on the remote servers.
## Getting started with Heroku
Before we can roll out any software on the Heroku cluster, we need to sign up and have to connect our development environment. Here are the most basic steps:
* [Sign up][0] for a Heroku account.
* [Install][1] the Heroku Toolbelt. This tool will let you create applications and is a handy way to configure them on the command line.
* Use the new binary to login. Run the following command on command line:`heroku login`
And that's it. You should now be able to do things like `heroku apps`. This should list all applications you've currently created on the Heroku cluster. If you've just created a new account, this should show you an empty list. [You can get further information about the registration process here][2].
## A minimal express application
In order to create a minimal express application, we need to install express first. We can do this via the following commands:
```bash
$ mkdir example-app
$ cd example-app
$ npm install express
$ node_modules/.bin/express . -f
$ npm install
$ node app.js
```
So now we have a default express application. If you point your browser to `http://localhost:8080`, you will see a tiny page welcoming you.
Next step: Deploy the application to Heroku.
## Deployment to Heroku
First of all, we need to add the right version of Node.JS and NPM to the `package.json`. The file should look similiar to this:
```js
{
"name": "application-name",
"version": "0.0.1",
"private": true,
"scripts": {
"start": "node app.js"
},
"dependencies": {
"express": "3.1.1",
"jade": "*"
},
"engines": {
"node": "0.8.x",
"npm": "1.1.x"
}
}
```
Now we can create a Heroku application and deploy to it:
```bash
$ echo "web: node app.js" > Procfile
$ echo "node_modules" > .gitignore
$ git init
$ git add .
$ git commit -m "initial commit"
$ heroku create
$ git push heroku master
$ heroku ps:scale web=1
$ heroku open
```
You should now see a browser with the same application as on your local machine.
## Spawning a database on Heroku
In order to get a database on Heroku we can use their CLI. Just run the following command and take a closer look at it's output:
```bash
$ heroku addons:add heroku-postgresql:dev
```
This will result in something like this:
```bash
Adding heroku-postgresql:dev on fast-dusk-7858... done, v5 (free)
Attached as HEROKU_POSTGRESQL_BRONZE_URL
Database has been created and is available
! This database is empty. If upgrading, you can transfer
! data from another database with pgbackups:restore.
Use `heroku addons:docs heroku-postgresql:dev` to view documentation.
```
What we will need is the color (sounds strange right?) of the database. In this case we just created a `bronze` one. That means, that we will have an environment variable `HEROKU_POSTGRESQL_BRONZE_URL` containing the URI of the database.
If you are interested in the URI, you can just run this command:
```bash
$ heroku config:get HEROKU_POSTGRESQL_BRONZE_URL
$ # => postgres://pfforbjhkrletg:aic5oO6Cran1g3hk6mJa5QqNZB@ec2-23-21-91-97.compute-1.amazonaws.com:5432/dek11b2j1g3mfb
```
## Adding Sequelize to the application
The following commands will install `sequelize`, the needed PostgreSQL library as well as the MySQL bindings. Also we will create a folder `models`, that will contain the model definitions.
```bash
$ npm install --save sequelize pg mysql
$ mkdir models
```
### app.js
In order to create a maintainable application, we will put all the database logic into the `models` folder. The application's main file will then just sync the models with the database and run the server. This way we don't clutter the application.
```js
var express = require('express')
, routes = require('./routes')
, user = require('./routes/user')
, http = require('http')
, path = require('path')
, db = require('./models');
var app = express();
// all environments
app.set('port', process.env.PORT || 3000);
app.set('views', __dirname + '/views');
app.set('view engine', 'jade');
app.use(express.favicon());
app.use(express.logger('dev'));
app.use(express.bodyParser());
app.use(express.methodOverride());
app.use(app.router);
app.use(express.static(path.join(__dirname, 'public')));
// development only
if ('development' === app.get('env')) {
app.use(express.errorHandler());
}
app.get('/', routes.index);
app.get('/users', user.list);
db.sequelize.sync().then(function() {
http.createServer(app).listen(app.get('port'), function(){
console.log('Express server listening on port ' + app.get('port'));
});
});
```
### models/index.js
The idea of this file is to configure a connection to the database and to collect all model definitions. Once everything is in place we will store the stuff in a singleton. This will make it possible to load the file whenever we need database access without running into issues with duplicated database access.
This file will also differ between the local machine and the Heroku server.
```js
if (!global.hasOwnProperty('db')) {
var Sequelize = require('sequelize')
, sequelize = null
if (process.env.HEROKU_POSTGRESQL_BRONZE_URL) {
// the application is executed on Heroku ... use the postgres database
sequelize = new Sequelize(process.env.HEROKU_POSTGRESQL_BRONZE_URL, {
dialect: 'postgres',
protocol: 'postgres',
port: match[4],
host: match[3],
logging: true //false
})
} else {
// the application is executed on the local machine ... use mysql
sequelize = new Sequelize('example-app-db', 'root', null)
}
global.db = {
Sequelize: Sequelize,
sequelize: sequelize,
User: sequelize.import(__dirname + '/user') 
// add your other models here
}
/*
Associations can be defined here. E.g. like this:
global.db.User.hasMany(global.db.SomethingElse)
*/
}
module.exports = global.db
```
### models/user.js
All the other models of our application will be located as separate files in the `models` folder. We will use the `import`-method of Sequelize to load those files.
```js
module.exports = function(sequelize, DataTypes) {
return sequelize.define("User", {
username: DataTypes.STRING
})
}
```
## Running Migrations
To run migrations on Heroku you must have the following entry in your config/config.json file:
```js
"production": {
"use_env_variable": "DATABASE_URL"
}
```
Which also means you must make sure your Heroku environment has [a promoted database.][3] Then from the command line run
```bash
$ heroku run bash
$ sequelize -m
```
## tl;dr
This article explains a straight-forward but maintainable approach for hosting an express application on Heroku. If you don't want to read all the stuff mentioned, just execute the following stuff and have fun.
```bash
$ mkdir example-app
$ cd example-app
$ npm install express
$ node_modules/.bin/express . -f
$ npm install
$ curl -s https://gist.github.com/sdepold/ced7d2a4a847f38901ef/raw/459c923dd0a14841c932bb95ff3be8a8170bd563/package.json > package.json
$ echo "web: node app.js" > Procfile
$ echo "node_modules" > .gitignore
$ npm install --save sequelize pg mysql
$ mkdir models
$ git init
$ git add .
$ git commit -m "initial commit"
$ heroku create
$ git push heroku master
$ heroku ps:scale web=1
$ heroku addons:add heroku-postgresql:dev
$ curl -s https://gist.github.com/sdepold/ced7d2a4a847f38901ef/raw/6db41e130a8b901cd0843bf52390b7cb11db5f15/app.js > app.js
$ curl -s https://gist.github.com/sdepold/ced7d2a4a847f38901ef/raw/26c5a94d74db4a242464b02aa8e0ae4b3bac6880/models-index.js > models/index.js
$ curl -s https://gist.github.com/sdepold/ced7d2a4a847f38901ef/raw/3b37b0e5d459b2e4b3833a63a018b600a1001795/models-user.js > models/user.js
$ clear
$ # Now run the following command and change HEROKU_POSTGRESQL_BRONZE_URL in
$ # the file "models/index.js" to its result:
$ heroku config|grep HEROKU_POSTGRESQL|cut -d : -f 1
$ git add .
$ git commit -m "sequelize application"
$ git push heroku master
$ heroku open
```
[0]: https://api.heroku.com/signup/devcenter
[1]: https://toolbelt.heroku.com/
[2]: https://devcenter.heroku.com/articles/quickstart
[3]: https://devcenter.heroku.com/articles/heroku-postgresql#establish-primary-db
\ No newline at end of file
table {
width:100%;
}
th:nth-child(1),
td:nth-child(1) {
width: 35%;
word-break: break-all;
}
td:nth-child(2),
td:nth-child(2) {
width: 20%;
word-break: break-word;
}
td,
th {
padding: 6px 13px;
border: 1px solid #ddd;
}
tr:nth-child(2n) {
background-color: #f8f8f8;
}
\ No newline at end of file
......@@ -11,20 +11,9 @@ program
.version('0.0.2')
.option('-f, --file [file]', 'Process a single file', '')
.option('-a, --all', 'Process all files, generate index etc. (default if no options are specified')
.option('-c, --clean', 'Remove all generated markdown and HTML files')
.option('-o --out [dir]', '', path.dirname(__filename))
.option('-o --out [dir]', '', path.dirname(__filename) + '/api')
.parse(process.argv);
if (program.clean) {
fs.readdirSync('docs/').forEach(function (file) {
if (file !== 'index.md' && path.extname(file) === '.md') {
fs.unlinkSync ('docs/' + file);
}
});
return;
}
var files;
if (program.file) {
files = [{file: program.file, output: 'tmp'}];
......
Hooks (also known as callbacks or lifecycle events), are functions which are called before and after calls in sequelize are executed. For example, if you want to always set a value on a model before saving it, you can add a `beforeUpdate` hook.
## Order of Operations
```
(1)
beforeBulkCreate(daos, fields, fn)
beforeBulkDestroy(daos, fields, fn)
beforeBulkUpdate(daos, fields, fn)
(2)
beforeValidate(dao, fn)
(-)
validate
(3)
afterValidate(dao, fn)
(4)
beforeCreate(dao, fn)
beforeDestroy(dao, fn)
beforeUpdate(dao, fn)
(-)
create
destroy
update
(5)
afterCreate(dao, fn)
afterDestroy(dao, fn)
afterUpdate(dao, fn)
(6)
afterBulkCreate(daos, fields, fn)
afterBulkDestory(daos, fields, fn)
afterBulkUpdate(daos, fields, fn)
```
## Declaring Hooks
There are currently three ways to programmatically add hooks. A hook function always runs asynchronousĺy, and can be resolved either by calling a callback (passed as the last argument),
or by returning a promise.
```js
// Method 1 via the .define() method
var User = sequelize.define('User', {
username: DataTypes.STRING,
mood: {
type: DataTypes.ENUM,
values: ['happy', 'sad', 'neutral']
}
}, {
hooks: {
beforeValidate: function(user, fn) {
user.mood = 'happy'
fn(null, user)
},
afterValidate: function(user, fn) {
user.username = 'Toni'
fn(null, user)
}
}
})
// Method 2 via the .hook() method
var User = sequelize.define('User', {
username: DataTypes.STRING,
mood: {
type: DataTypes.ENUM,
values: ['happy', 'sad', 'neutral']
}
})
User.hook('beforeValidate', function(user, fn) {
user.mood = 'happy'
fn(null, user)
})
User.hook('afterValidate', function(user) {
return sequelize.Promise.reject("I'm afraid I can't let you do that!")
})
// Method 3 via the direct method
var User = sequelize.define('User', {
username: DataTypes.STRING,
mood: {
type: DataTypes.ENUM,
values: ['happy', 'sad', 'neutral']
}
})
User.beforeValidate(function(user) {
user.mood = 'happy'
return sequelize.Promise.resolve(user)
})
User.afterValidate(function(user, fn) {
user.username = 'Toni'
fn(null, user)
})
```
### Instance hooks
The following hooks will emit whenever you're editing a single object...
```
beforeValidate
afterValidate
beforeCreate / beforeUpdate / beforeDestroy
afterCreate / afterUpdate / afterDestroy
```
```js
// ...define ...
User.beforeCreate(function(user, fn) {
if (user.accessLevel > 10 && user.username !== "Boss") {
return fn("You can't grant this user an access level above 10!")
}
return fn()
})
```
This example will emit an error:
```js
User.create({username: 'Not a Boss', accessLevel: 20}).error(function(err) {
console.log(err) // You can't grant this user an access level above 10!
})
```
The following example would emit a success event:
```js
User.create({username: 'Boss', accessLevel: 20}).success(function(user) {
console.log(user) // user object with username as Boss and accessLevel of 20
})
```
### Model hooks
Sometimes you'll be editing more than one record at a time by utilizing the `bulkCreate, update, destroy` methods on the model. The following will emit whenever you're using one of those methods.
```
beforeBulkCreate / beforeBulkUpdate / beforeBulkDestroy
afterBulkCreate / afterBulkUpdate / afterBulkDestroy
```
If you want to emit hooks for each individual record, along with the bulk hooks you can pass `individualHooks: true` to the call.
```js
Model.destroy({accessLevel: 0}, {individualHooks: true})
// Will select all records that are about to be deleted and emit before- + after- Destroy on each instance
Model.update({username: 'Toni'}, {accessLevel: 0}, {individualHooks: true})
// Will select all records that are about to be updated and emit before- + after- Update on each instance
Model.bulkCreate({accessLevel: 0}, null, {individualHooks: true})
// Will select all records that are about to be deleted and emit before- + after- Create on each instance
```
Some model hooks have two or three parameters sent to each hook depending on it's type.
```js
Model.beforeBulkCreate(function(records, fields, fn) {
// records = the first argument sent to .bulkCreate
// fields = the second argument sent to .bulkCreate
})
Model.bulkCreate([
{username: 'Toni'}, // part of records argument
{username: 'Tobi'} // part of records argument
], ['username'] /* part of fields argument */)
Model.beforeBulkUpdate(function(attributes, where, fn) {
// attributes = first argument sent to Model.update
// where = second argument sent to Model.update
})
Model.update({gender: 'Male'} /*attributes argument*/, {username: 'Tom'} /*where argument*/)
Model.beforeBulkDestroy(function(whereClause, fn) {
// whereClause = first argument sent to Model.destroy
})
Model.destroy({username: 'Tom'} /*whereClause argument*/)
```
## Associations
For the most part hooks will work the same for instances when being associated except a few things
1. When using add/set\[s\] functions the beforeUpdate/afterUpdate hooks will run.
2. The only way to call beforeDestroy/afterDestroy hooks are on associations with `onDelete: 'cascade'` and the option `hooks: true`. For instance:
```js
var Projects = sequelize.define('Projects', {
title: DataTypes.STRING
})
var Tasks = sequelize.define('Tasks', {
title: DataTypes.STRING
})
Projects.hasMany(Tasks, {onDelete: 'cascade', hooks: true})
Tasks.belongsTo(Projects)
```
This code will run beforeDestroy/afterDestroy on the Tasks table. Sequelize, by default, will try to optimize your queries as much as possible.
When calling cascade on delete, Sequelize will simply execute a
```sql
DELETE FROM `table` WHERE associatedIdentifiier = associatedIdentifier.primaryKey
```
However, adding `hooks: true` explicitly tells Sequelize that optimization is not of your concern and will perform a `SELECT` on the associated objects and destroy each instance one by one in order to be able to call the hooks with the right parameters.
## A Note About Transactions
Note that many model operations in Sequelize allow you to specify a transaction in the options parameter of the method. If a transaction _is_ specified in the original call, it will be present in the options parameter passed to the hook function. For example, consider the following snippet:
```js
// Here we use the promise-style of async hooks rather than
// the callback.
User.hook('afterCreate', function(user, options) {
// 'trans' will be available in options.transaction
// This operation will be part of the same transaction as the
// original User.create call.
return User.update({
mood: 'sad'
}, {
where: {
id: user.id
},
transaction: options.transaction
});
});
sequelize.transaction(function(trans) {
User.create({
username: 'someguy',
mood: 'happy'
}, {
transaction: trans
});
});
```
If we had not included the transaction option in our call to `User.update` in the preceding code, no change would have occurred, since our newly created user does not exist in the database until the pending transaction has been committed.
### Internal Transactions
It is very important to recognize that sequelize may make use of transactions internally for certain operations such as `Model.findOrCreate`. If your hook functions execute read or write operations that rely on the object's presence in the database, or modify the object's stored values like the example in the preceding section, you should always specify `{ transaction: options.transaction }`.
If the hook has been called in the process of a transacted operation, this makes sure that your dependent read/write is a part of that same transaction. If the hook is not transacted, you have simply specified `{ transaction: null }` and can expect the default behaviour.
\ No newline at end of file
## Installation
You have two options to install Sequelize:
1&period; Install it via NPM:
```bash
# Use npm on the commandline:
$ npm install sequelize
// Then require the installed library in your application code:
var Sequelize = require("sequelize")
```
2&period; Download the code from the git repository and require it's entry file index&period;js&colon;
```bash
# Checkout the current code from the repository using the commandline
$ cd path/to/lib
$ git clone git://github.com/sequelize/sequelize.git
// Then require the installed library in your application code&colon;
var Sequelize = require(__dirname + "/lib/sequelize/index")
```
This will make the class `Sequelize` available.
\ No newline at end of file
Sequelize `2.0.0` introduces a new CLI which is based on [gulp][0] and combines [sequelize-cli][1] and [gulp-sequelize][2]. The CLI ships support for migrations and project bootstrapping. With migrations you can transfer your existing database into another state and vice versa: Those state transitions are saved in migration files, which describe the way how to get to the new state and how to revert the changes in order to get back to the old state.
## The CLI
In order to use the CLI you need to install the respective package:
```bash
$ npm install --save sequelize-cli
```
The CLI currently supports the following commands:
```bash
$ sequelize db:migrate # Run pending migrations.
$ sequelize db:migrate:undo # Revert the last migration run.
$ sequelize help # Display this help text.
$ sequelize init # Initializes the project.
$ sequelize migration:create # Generates a new migration file.
$ sequelize version # Prints the version number.
```
Further and more detailled information about the available commands
can be obtained via the help command:
```bash
$ sequelize help:init
$ sequelize help:db:migrate
$ sequelize help:db:migrate:undo
# etc
```
The latter one for example will print out the following output:
```bash
Sequelize [CLI: v0.0.2, ORM: v1.7.5]
COMMANDS
sequelize db:migrate:undo -- Revert the last migration run.
DESCRIPTION
Revert the last migration run.
OPTIONS
--env The environment to run the command in. Default: development
--options-path The path to a JSON file with additional options. Default: none
--coffee Enables coffee script support. Default: false
--config The path to the config file. Default: config/config.json
```
## Skeleton
The following skeleton shows a typical migration file&period; All migrations are expected to be located in a folder called `migrations` at the very top of the project&period; The sequelize binary can generate a migration skeleton&period; See the aboves section for more details&period;
```js
module.exports = {
up: function(migration, DataTypes, done) {
// logic for transforming into the new state
done() // sets the migration as finished
},
 
down: function(migration, DataTypes, done) {
// logic for reverting the changes
done() // sets the migration as finished
}
}
```
The passed `migration` object can be used to modify the database&period; The `DataTypes` object stores the available data types such as `STRING` or `INTEGER`&period; The third parameter is a callback function which needs to be called once everything was executed&period; The first parameter of the callback function can be used to pass a possible error&period; In that case&comma; the migration will be marked as failed&period; Here is some code&colon;
```js
module.exports = {
up: function(migration, DataTypes, done) {
migration.dropAllTables().complete(done)
 
// equals:
migration.dropAllTables().complete(function(err) {
if (err) {
done(err)
} else {
done(null)
}
})
}
}
```
The available methods of the migration object are the following&period;
## Functions
Using the `migration` object describe before&comma; you will have access to most of already introduced functions&period; Furthermore there are some other methods&comma; which are designed to actually change the database schema&period;
### createTable&lpar;tableName&comma; attributes&comma; options&rpar;
This method allows creation of new tables&period; It is allowed to pass simple or complex attribute definitions&period; You can define the encoding of the table and the table's engine via options
```js
migration.createTable(
'nameOfTheNewTable',
{
id: {
type: DataTypes.INTEGER,
primaryKey: true,
autoIncrement: true
},
createdAt: {
type: DataTypes.DATE
},
updatedAt: {
type: DataTypes.DATE
},
attr1: DataTypes.STRING,
attr2: DataTypes.INTEGER,
attr3: {
type: DataTypes.BOOLEAN,
defaultValue: false,
allowNull: false
}
},
{
engine: 'MYISAM', // default: 'InnoDB'
charset: 'latin1' // default: null
}
)
```
### dropTable&lpar;tableName&rpar;
This method allows deletion of an existing table&period;
```js
migration.dropTable('nameOfTheExistingTable')
```
### dropAllTables&lpar;&rpar;
This method allows deletion of all existing tables in the database&period;
```js
migration.dropAllTables()
```
### renameTable&lpar;before&comma; after&rpar;
This method allows renaming of an existing table&period;
```js
migration.renameTable('Person', 'User')
```
### showAllTables&lpar;&rpar;
This method returns the name of all existing tables in the database&period;
```js
migration.showAllTables().success(function(tableNames) {})
```
### describeTable&lpar;tableName&rpar;
This method returns an array of hashes containing information about all attributes in the table&period;
```js
migration.describeTable('Person').success(function(attributes) {
/*
attributes will be something like:
 
{
name: {
type: 'VARCHAR(255)', // this will be 'CHARACTER VARYING' for pg!
allowNull: true,
defaultValue: null
},
isBetaMember: {
type: 'TINYINT(1)', // this will be 'BOOLEAN' for pg!
allowNull: false,
defaultValue: false
}
}
*/
})
```
### addColumn&lpar;tableName&comma; attributeName&comma; dataTypeOrOptions&rpar;
This method allows adding columns to an existing table&period; The data type can be simple or complex&period;
```js
migration.addColumn(
'nameOfAnExistingTable',
'nameOfTheNewAttribute',
DataTypes.STRING
)
 
// or
 
migration.addColumn(
'nameOfAnExistingTable',
'nameOfTheNewAttribute',
{
type: DataTypes.STRING,
allowNull: false
}
)
```
### removeColumn&lpar;tableName&comma; attributeName&rpar;
This method allows deletion of a specific column of an existing table&period;
```js
migration.removeColumn('Person', 'signature')
```
### changeColumn&lpar;tableName&comma; attributeName&comma; dataTypeOrOptions&rpar;
This method changes the meta data of an attribute&period; It is possible to change the default value&comma; allowance of null or the data type&period; Please make sure&comma; that you are completely describing the new data type&period; Missing information are expected to be defaults&period;
```js
migration.changeColumn(
'nameOfAnExistingTable',
'nameOfAnExistingAttribute',
DataTypes.STRING
)
 
// or
 
migration.changeColumn(
'nameOfAnExistingTable',
'nameOfAnExistingAttribute',
{
type: DataTypes.FLOAT,
allowNull: false,
default: 0.0
}
)
```
### renameColumn&lpar;tableName&comma; attrNameBefore&comma; attrNameAfter&rpar;
This methods allows renaming attributes&period;
```js
migration.renameColumn('Person', 'signature', 'sig')
```
### addIndex&lpar;tableName&comma; attributes&comma; options&rpar;
This methods creates indexes for specific attributes of a table&period; The index name will be automatically generated if it is not passed via in the options &lpar;see below&rpar;&period;
```js
// This example will create the index person_firstname_lastname
migration.addIndex('Person', ['firstname', 'lastname'])
// This example will create a unique index with the name SuperDuperIndex using the optional 'options' field.
// Possible options:
// - indicesType: UNIQUE|FULLTEXT|SPATIAL
// - indexName: The name of the index. Default is __
// - parser: For FULLTEXT columns set your parser
// - indexType: Set a type for the index, e.g. BTREE. See the documentation of the used dialect
migration.addIndex(
'Person',
['firstname', 'lastname'],
{
indexName: 'SuperDuperIndex',
indicesType: 'UNIQUE'
}
)
```
### removeIndex&lpar;tableName&comma; indexNameOrAttributes&rpar;
This method deletes an existing index of a table&period;
```js
migration.removeIndex('Person', 'SuperDuperIndex')
 
// or
 
migration.removeIndex('Person', ['firstname', 'lastname'])
```
## Programmatic use
If you need to interact with the migrator within your code, you can easily achieve that via `sequelize.getMigrator`. You can specify the path to your migrations as well as a pattern which represents the files that contain the migrations.
```js
var migrator = sequelize.getMigrator({
path: process.cwd() + '/database/migrations',
filesFilter: /\.coffee$/
})
```
Once you have a migrator object, you can run its migration with `migrator.migrate`. By default, this will execute all the up methods within your pending migrations. If you want to rollback a migration, just call it like this:
```js
migrator
.migrate({ method: 'down' })
.success(function() {
// The migrations have been executed!
})
```
[0]: http://gulpjs.com/
[1]: https://github.com/sequelize/cli
[2]: https://github.com/sequelize/gulp-sequelize
\ No newline at end of file
## Utils / Lodash.js
Sequelize comes with some handy utils including references to `lodash` as well as some individual helpers&period; You can access them via `Sequelize.Utils`&period;
You can access all the methods of lodash like this&colon;
```js
Sequelize.Utils._.each(/* ... */)
Sequelize.Utils._.map(/* ... */)
Sequelize.Utils._...
```
Check out the [Lodash][0] page for further information&period;
[0]: http://lodash.com/
## Compatibility
Sequelize is compatible to the following versions of Node.JS:
* 0.8.x
* 0.10.x
## Asynchronicity
Since`v1&period;3&period;0`there are multiple ways of adding listeners to asynchronous requests&period; First of all&comma; each time you call a finder method or save an object&comma; sequelize triggers asynchronous logic&period; To react to the success or the failure &lpar;or both&rpar; of the request&comma; you can do the following&colon;
// the old, pre-v1.3.0 way
Model.findAll().on('success', function(models) { /* foo */ })
Model.findAll().on('failure', function(err) { /* bar */ })
 
// the new, >=v1.3.0 way
// each one is valid
Model.findAll().on('success', function(models) { /* foo */ })
Model.findAll().success(function(models) { /* foo */ })
Model.findAll().ok(function(models) { /* foo */ })
 
// Model.findAll().on('failure', function(err) { /* bar */ }) ==> invalid since v1.5.0
Model.findAll().on('error', function(err) { /* bar */ }) // ==> new since v1.5.0
Model.findAll().error(function(err) { /* bar */ })
Model.findAll().failure(function(err) { /* bar */ })
Model.findAll().fail(function(err) { /* bar */ })
 
Model.findAll().complete(function(err, result) { /* bar */ })
Model.findAll().done(function(err, result) { /* bar */ })
 
// As of 1.7.0 we support Promises/A
var self = User
 
user.find(1).then(function(user1) {
return user1.increment(['aNumber'], 2)
}).then(function(user2) {
return user.find(1)
}).then(function(user3) {
console.log(user3.aNumber) // 2
}, function(err) {
// err...
})
 
 
// For functions with multiple success values (e.g. findOrCreate) there is also spread
 
user.findOrCreate(...).spread(function(user, wasCreated) {
// all arguments are passed
})
user.findOrCreate(...).then(function(user) {
// only the first argument is passed
})
**Please notice&colon;**Since v1&period;5&period;0 the 'error' event is used to notify about errors&period; If such events aren't caught however&comma; Node&period;JS will throw an error&period; So you would probably like to catch them &colon;D
### Additional links
If you want to keep track about latest development of sequelize or to just discuss things with other sequelize users you might want to take a look at the following resources&colon;
* [Twitter&colon; &commat;sdepold][0]
* [Twitter&colon; &commat;sequelizejs][1]
* [ADN&colon; &commat;sdepold][2]
* [IRC&colon; sequelizejs&commat;freenode&period;net][3]
* [XING][4]
* [Facebook][5]
## Companies & Projects
Here is a list of companies and projects that are using Sequelize in real world applications&colon;
### [Shutterstock][6]
Shutterstock Images LLC is a leading global provider of high-quality stock footage&comma; stock photography&comma; vectors and illustrations to creative industry professionals around the world&period; Shutterstock works closely with its growing contributor community of artists&comma; photographers&comma; videographers and illustrators to curate a global marketplace for royalty-free&comma; top-quality imagery&period; Shutterstock adds tens of thousands of rights-cleared images and footage clips each week&comma; with more than 18 million files currently available&period;
### [Clevertech][7]
Clevertech builds web and mobile applications for startups using Lean and Agile methodologies. Clevertech relies on Sequelize for its applications, its speed, versatility and data flexibility. Clevertech contributes back to open source development and its expert developers support the continuing effort to make sequelize the best ORM for Node projects.
### [Metamarkets][8]
Metamarkets enables buyers and sellers of digital media to visualize insights and make decisions with real-time pricing&comma; performance&comma; and audience data&period;
### [filsh][10]
filsh allows you to download online videos from various video
portals like YouTube, Vimeo and Dailymotion in a format you like.
No software required.
### [Using sequelize&quest;][11]
If you want to get listed here&comma; just drop me a line or send me a pull-request on Github&excl;
[0]: http://twitter.com/sdepold
[1]: http://twitter.com/sequelizejs
[2]: https://alpha.app.net/sdepold
[3]: irc://irc.freenode.net/sequelizejs
[4]: https://www.xing.com/net/priec1b5cx/sequelize
[5]: https://www.facebook.com/sequelize
[6]: http://www.shutterstock.com
[7]: http://www.clevertech.biz
[8]: http://metamarkets.com/
[9]: https://innofluence.com
[10]: http://filsh.net
[11]: https://github.com/sequelize/sequelize/tree/gh-pages
\ No newline at end of file
TODO - something about how promises work
\ No newline at end of file
## Transactions
```js
sequelize.transaction(function(t) {
// we just opened a new connection to the database which is transaction exclusive.
// also we send some first transaction queries to the database.
// do some async stuff ...
// if everything is ok ... commit the transaction
t.commit().success(function() {})
// if something failed ... rollback the transaction
t.rollback().success(function() {})
// the commit / rollback will emit events which can be observed via:
t.done(function() {
/* we will be here once the transaction
has been committed / reverted */
})
})
sequelize.transaction(function(t) {
User.create({ username: 'foo' }, { transaction: t }).success(function() {
// this user will only be available inside the session
User.all({ transaction: t }) // will return the user
User.all() // will not return the user
})
})
```
\ No newline at end of file
No preview for this file type
# Imprint - Boring legal stuff for the rest of us.
As there are people who are suing for fun and glory, you can find the respective information about the author of the page right here. Have fun reading ...
## AUTHOR(S)
```
Main author:
Sascha Depold
Uhlandstr. 122
10717 Berlin
sascha [at] depold [dot] com
```
## INHALTLICHE VERANTWORTUNG
```
Ich übernehme keine Haftung für ausgehende Links.
Daher musst du dich bei Problemen an deren Betreiber wenden!
```
\ No newline at end of file
The Sequelize library provides easy access to MySQL, MariaDB, SQLite or PostgreSQL databases by mapping database entries to objects and vice versa. To put it in a nutshell, it's an ORM (Object-Relational-Mapper). The library is written entirely in JavaScript and can be used in the Node.JS environment.
## Easy installation
```bash
$ npm install sequelize
$ npm install mysql
```
## Simple usage
```js
var Sequelize = require('sequelize')
, sequelize = new Sequelize('database', 'username', 'password')
var User = sequelize.define('User', {
username: Sequelize.STRING,
birthday: Sequelize.DATE
})
sequelize.sync().success(function() {
User.create({
username: 'sdepold',
birthday: new Date(1986, 06, 28)
}).success(function(sdepold) {
console.log(sdepold.values)
})
})
```
## Trusted and used by
[![](/images/shutterstock.png)](docs/misc#shutterstock)
[![](/images/clevertech.png)](docs/misc#clevertech)
[![](/images/metamarkets.png)](docs/misc#metamarkets)
[![](/images/filsh.png)](docs/misc#filsh)
(c) Sascha Depold, [et al.](https://github.com/sequelize/sequelize-doc/graphs/contributors) 2006 - 2014 [Imprint](imprint)
\ No newline at end of file
<!DOCTYPE html>
<!--[if IE 8]><html class="no-js lt-ie9" lang="en" > <![endif]-->
<!--[if gt IE 8]><!--> <html class="no-js" lang="en" > <!--<![endif]-->
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
{% block htmltitle %}
<title>{{ page_title }}</title>
{% endblock %}
{# CSS #}
<link href='https://fonts.googleapis.com/css?family=Lato:400,700|Roboto+Slab:400,700|Inconsolata:400,700' rel='stylesheet' type='text/css'>
<link rel="stylesheet" href="{{ base_url }}/css/theme.css" type="text/css" />
{%- for path in extra_css %}
<link href="{{ path }}" rel="stylesheet">
{%- endfor %}
<script src="//cdnjs.cloudflare.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="//cdnjs.cloudflare.com/ajax/libs/modernizr/2.8.3/modernizr.min.js"></script>
<script src="{{ base_url }}/js/theme.js"></script>
{%- for path in extra_javascript %}
<script src="{{ path }}"></script>
{%- endfor %}
<style>
body {font-size: 90%;}
pre, code {font-size: 100%;}
h3, h4, h5, h6 {color: #2980b9; font-weight: 300}
</style>
{%- block extrahead %} {% endblock %}
</head>
<body class="wy-body-for-nav" role="document">
<div class="wy-grid-for-nav">
{# SIDE NAV, TOGGLES ON MOBILE #}
<nav data-toggle="wy-nav-shift" class="wy-nav-side stickynav">
<div class="wy-side-nav-search">
<a href="{{ homepage_url }}" class="icon icon-home"> {{ site_name }}</a>
{% include "searchbox.html" %}
</div>
<div class="wy-menu wy-menu-vertical" data-spy="affix" role="navigation" aria-label="main navigation">
{% include "toc.html" %}
</div>
&nbsp;
</nav>
<section data-toggle="wy-nav-shift" class="wy-nav-content-wrap">
{# MOBILE NAV, TRIGGLES SIDE NAV ON TOGGLE #}
<nav class="wy-nav-top" role="navigation" aria-label="top navigation">
<i data-toggle="wy-nav-top" class="icon icon-reorder"></i>
<a href="{{ homepage_url }}">{{ project }}</a>
</nav>
{# PAGE CONTENT #}
<div class="wy-nav-content">
<div class="rst-content">
{% include "breadcrumbs.html" %}
<div role="main">
<div class="section">
{{ content }}
</div>
</div>
{%- block footer %}
{% include "footer.html" %}
{% endblock %}
</div>
</div>
</section>
</div>
<div class="rst-versions" role="note" style="cursor: pointer">
<span class="rst-current-version" data-toggle="rst-current-version">
{% if repo_name == 'GitHub' %}
<a class="icon icon-github" style="float: left; color: #fcfcfc"> GitHub</a>
{% elif repo_name == 'Bitbucket' %}
<a class="icon icon-bitbucket" style="float: left; color: #fcfcfc"> BitBucket</a>
{% endif %}
<span><a href="" style="color: #fcfcfc;">&laquo; Previous</a></span>
<span style="margin-left: 15px"><a href="" style="color: #fcfcfc">Next &raquo;</a></span>
</span>
</div>
</body>
</html>
<div role="navigation" aria-label="breadcrumbs navigation">
<ul class="wy-breadcrumbs">
<li><a href="{{ homepage_url }}">Docs</a> &raquo;</li>
<li>{{ current_page.title }}</li>
<li class="wy-breadcrumbs-aside">
{% if repo_url %}
{% if repo_name == 'GitHub' %}
<a href="{{ repo_url }}" class="icon icon-github"> Edit on GitHub</a>
{% elif repo_name == 'Bitbucket' %}
<a href="{{ repo_url }}" class="icon icon-bitbucket"> Edit on BitBucket</a>
{% endif %}
{% endif %}
</li>
</ul>
<hr/>
</div>
This diff could not be displayed because it is too large.
<footer>
{% if next_page or previous_page %}
<div class="rst-footer-buttons" role="navigation" aria-label="footer navigation">
{% if next_page %}
<a href="{{ next_page.url }}" class="btn btn-neutral float-right" title="{{ next_page.title }}"/>Next <span class="icon icon-circle-arrow-right"></span></a>
{% endif %}
{% if previous_page %}
<a href="{{ previous_page.url }}" class="btn btn-neutral" title="{{ previous_page.title }}"><span class="icon icon-circle-arrow-left"></span> Previous</a>
{% endif %}
</div>
{% endif %}
<hr/>
<div role="contentinfo">
<p>
<!-- Copyright etc -->
</p>
</div>
Built with <a href="http://www.mkdocs.org">MkDocs</a>, using a <a href="https://github.com/snide/sphinx_rtd_theme">theme</a> provided by <a href="https://readthedocs.org">Read the Docs</a>.
</footer>
No preview for this file type
$( document ).ready(function() {
// Shift nav in mobile when clicking the menu.
$(document).on('click', "[data-toggle='wy-nav-top']", function() {
$("[data-toggle='wy-nav-shift']").toggleClass("shift");
$("[data-toggle='rst-versions']").toggleClass("shift");
});
// Close menu when you click a link.
$(document).on('click', ".wy-menu-vertical .current ul li a", function() {
$("[data-toggle='wy-nav-shift']").removeClass("shift");
$("[data-toggle='rst-versions']").toggleClass("shift");
});
$(document).on('click', "[data-toggle='rst-current-version']", function() {
$("[data-toggle='rst-versions']").toggleClass("shift-up");
});
// Make tables responsive
$("table.docutils:not(.field-list)").wrap("<div class='wy-table-responsive'></div>");
});
window.SphinxRtdTheme = (function (jquery) {
var stickyNav = (function () {
var navBar,
win,
stickyNavCssClass = 'stickynav',
applyStickNav = function () {
if (navBar.height() <= win.height()) {
navBar.addClass(stickyNavCssClass);
} else {
navBar.removeClass(stickyNavCssClass);
}
},
enable = function () {
applyStickNav();
win.on('resize', applyStickNav);
},
init = function () {
navBar = jquery('nav.wy-nav-side:first');
win = jquery(window);
};
jquery(init);
return {
enable : enable
};
}());
return {
StickyNav : stickyNav
};
}($));
{#
basic/search.html
~~~~~~~~~~~~~~~~~
Template for the search page.
:copyright: Copyright 2007-2013 by the Sphinx team, see AUTHORS.
:license: BSD, see LICENSE for details.
#}
{%- extends "layout.html" %}
{% set title = _('Search') %}
{% set script_files = script_files + ['_static/searchtools.js'] %}
{% block extrahead %}
<script type="text/javascript">
jQuery(function() { Search.loadIndex("{{ pathto('searchindex.js', 1) }}"); });
</script>
{# this is used when loading the search index using $.ajax fails,
such as on Chrome for documents on localhost #}
<script type="text/javascript" id="searchindexloader"></script>
{{ super() }}
{% endblock %}
{% block body %}
<noscript>
<div id="fallback" class="admonition warning">
<p class="last">
{% trans %}Please activate JavaScript to enable the search
functionality.{% endtrans %}
</p>
</div>
</noscript>
{% if search_performed %}
<h2>{{ _('Search Results') }}</h2>
{% if not search_results %}
<p>{{ _('Your search did not match any documents. Please make sure that all words are spelled correctly and that you\'ve selected enough categories.') }}</p>
{% endif %}
{% endif %}
<div id="search-results">
{% if search_results %}
<ul>
{% for href, caption, context in search_results %}
<li>
<a href="{{ pathto(item.href) }}">{{ caption }}</a>
<p class="context">{{ context|e }}</p>
</li>
{% endfor %}
</ul>
{% endif %}
</div>
{% endblock %}
<div role="search">
<form id ="rtd-search-form" class="wy-form" action="" method="get">
<input type="text" name="q" placeholder="Search docs" />
<input type="hidden" name="check_keywords" value="yes" />
<input type="hidden" name="area" value="default" />
</form>
</div>
<ul class="current">
{% for nav_item in nav %}
{% if nav_item.children %}
<span class="toctree-l0">{{ nav_item.title }}</span>
{% for nav_item in nav_item.children %}
<li class="toctree-l1 {% if nav_item.active%}current{%endif%}">
<a class="{% if nav_item.active%}current{%endif%}" href="{{ nav_item.url }}">{{ nav_item.title }}</a>
{% if nav_item == current_page %}
<ul>
{% for toc_item in toc %}
<li class="toctree-l2"><a href="{{ toc_item.url }}">{{ toc_item.title }}</a></li>
{% for toc_item in toc_item.children %}
<li><a class="toctree-l3" href="{{ toc_item.url }}">{{ toc_item.title }}</a></li>
{% endfor %}
{% endfor %}
</ul>
{% endif %}
</li>
{% endfor %}
{% else %}
<li class="toctree-l1 {% if nav_item.active%}current{%endif%}">
<a class="{% if nav_item.active%}current{%endif%}" href="{{ nav_item.url }}">{{ nav_item.title }}</a>
</li>
{% endif %}
{% endfor %}
</ul>
git+https://github.com/dart-lang/py-gfm.git
site_name: Sequelize - node.js ORM for Postgres, MySQl, MariaDB and SQLite
theme_dir: docs/readthedocs_theme
repo_url: https://github.com/sequelize/sequelize
site_favicon: favicon.ico
markdown_extensions: [gfm]
extra_css:
- css/custom.css
extra_javascript:
- //cdnjs.cloudflare.com/ajax/libs/highlight.js/8.4/highlight.min.js
pages:
- ['index.md', 'Home', 'Welcome']
- ['imprint.md', 'Home', 'Imprint']
- ['articles/getting-started.md', 'Articles', 'Getting started']
- ['articles/heroku.md', 'Articles', 'Heroku']
- ['articles/express.md', 'Articles', 'Usage with Express.JS']
- ['docs/installation.md', 'Docs', 'Installation']
- ['docs/usage.md', 'Docs', 'Usage']
- ['docs/promises.md', 'Docs', 'Promises']
- ['docs/models.md', 'Docs', 'Models']
- ['docs/instances.md', 'Docs', 'Instances']
- ['docs/associations.md', 'Docs', 'Associations']
- ['docs/hooks.md', 'Docs', 'Hooks']
- ['docs/transactions.md', 'Docs', 'Transactions']
- ['docs/migrations.md', 'Docs', 'Migrations']
- ['docs/misc.md', 'Docs', 'Misc']
- ['api/sequelize.md', 'API', 'Sequelize']
- ['api/model.md', 'API', 'Model']
- ['api/instance.md', 'API', 'Instance']
- ['api/associations.md', 'API', 'Associations']
- ['api/hooks.md', 'API', 'Hooks']
- ['api/promise.md', 'API', 'Promise']
- ['api/transaction.md', 'API', 'Transaction']
- ['api/datatypes.md', 'API', 'Datatypes']
- ['api/errors.md', 'API', 'Errors']
......@@ -76,7 +76,8 @@
"main": "index",
"scripts": {
"test": "make all",
"docs": "node_modules/.bin/yuidoc . -o docs"
"docs": "node docs/docs-generator.js",
"prepublish": "docs"
},
"engines": {
"node": ">=0.6.21"
......
Markdown is supported
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!