From 029cfe5e0789dc9c229d50bec47d4b3b518eb445 Mon Sep 17 00:00:00 2001 From: torianyap Date: Mon, 26 Oct 2020 12:06:24 +0700 Subject: [PATCH 01/22] first commit --- .gitignore | 1 + README.md | 37 ++- package-lock.json | 618 ++++++++++++++++++++++++++++++++++++++++++++++ package.json | 26 ++ server/readme.md | 2 +- 5 files changed, 682 insertions(+), 2 deletions(-) create mode 100644 .gitignore create mode 100644 package-lock.json create mode 100644 package.json diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..b512c09 --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +node_modules \ No newline at end of file diff --git a/README.md b/README.md index b83fed8..af5b9fa 100644 --- a/README.md +++ b/README.md @@ -1 +1,36 @@ -# FancyTodo \ No newline at end of file +# FancyTodo + +**Show List Todo** +---- + Return JSON data about all todos + +* **URL** + + /todos + +* **Method:** + + `GET` + +* **Success Response:** + + * **Code:** 200
+ **Content:** `{ id : 12 }` + +* **Error Response:** + + * **Code:** 401 UNAUTHORIZED
+ **Content:** `{ error : "Log in" }` + + OR + + * **Code:** 422 UNPROCESSABLE ENTRY
+ **Content:** `{ error : "Email Invalid" }` + +* **Sample Call:** + + <_Just a sample call to your endpoint in a runnable format ($.ajax call or a curl request) - this makes life easier and more predictable._> + +* **Notes:** + + <_This is where all uncertainties, commentary, discussion etc. can go. I recommend timestamping and identifying oneself when leaving comments here._> \ No newline at end of file diff --git a/package-lock.json b/package-lock.json new file mode 100644 index 0000000..401eeec --- /dev/null +++ b/package-lock.json @@ -0,0 +1,618 @@ +{ + "name": "FancyTodo", + "version": "1.0.0", + "lockfileVersion": 1, + "requires": true, + "dependencies": { + "@types/node": { + "version": "14.14.3", + "resolved": "https://registry.npmjs.org/@types/node/-/node-14.14.3.tgz", + "integrity": "sha512-33/L34xS7HVUx23e0wOT2V1qPF1IrHgQccdJVm9uXGTB9vFBrrzBtkQymT8VskeKOxjz55MSqMv0xuLq+u98WQ==" + }, + "accepts": { + "version": "1.3.7", + "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.7.tgz", + "integrity": "sha512-Il80Qs2WjYlJIBNzNkK6KYqlVMTbZLXgHx2oT0pU/fjRHyEp+PEfEPY0R3WCwAGVOtauxh1hOxNgIf5bv7dQpA==", + "requires": { + "mime-types": "~2.1.24", + "negotiator": "0.6.2" + } + }, + "any-promise": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/any-promise/-/any-promise-1.3.0.tgz", + "integrity": "sha1-q8av7tzqUugJzcA3au0845Y10X8=" + }, + "array-flatten": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", + "integrity": "sha1-ml9pkFGx5wczKPKgCJaLZOopVdI=" + }, + "body-parser": { + "version": "1.19.0", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.19.0.tgz", + "integrity": "sha512-dhEPs72UPbDnAQJ9ZKMNTP6ptJaionhP5cBb541nXPlW60Jepo9RV/a4fX4XWW9CuFNK22krhrj1+rgzifNCsw==", + "requires": { + "bytes": "3.1.0", + "content-type": "~1.0.4", + "debug": "2.6.9", + "depd": "~1.1.2", + "http-errors": "1.7.2", + "iconv-lite": "0.4.24", + "on-finished": "~2.3.0", + "qs": "6.7.0", + "raw-body": "2.4.0", + "type-is": "~1.6.17" + } + }, + "buffer-writer": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/buffer-writer/-/buffer-writer-2.0.0.tgz", + "integrity": "sha512-a7ZpuTZU1TRtnwyCNW3I5dc0wWNC3VR9S++Ewyk2HHZdrO3CQJqSpd+95Us590V6AL7JqUAH2IwZ/398PmNFgw==" + }, + "bytes": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.0.tgz", + "integrity": "sha512-zauLjrfCG+xvoyaqLoV8bLVXXNGC4JqlxFCutSDWA6fJrTo2ZuvLYTqZ7aHBLZSMOopbzwv8f+wZcVzfVTI2Dg==" + }, + "content-disposition": { + "version": "0.5.3", + "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.3.tgz", + "integrity": "sha512-ExO0774ikEObIAEV9kDo50o+79VCUdEB6n6lzKgGwupcVeRlhrj3qGAfwq8G6uBJjkqLrhT0qEYFcWng8z1z0g==", + "requires": { + "safe-buffer": "5.1.2" + } + }, + "content-type": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.4.tgz", + "integrity": "sha512-hIP3EEPs8tB9AT1L+NUqtwOAps4mk2Zob89MWXMHjHWg9milF/j4osnnQLXBCBFBk/tvIG/tUc9mOUJiPBhPXA==" + }, + "cookie": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.0.tgz", + "integrity": "sha512-+Hp8fLp57wnUSt0tY0tHEXh4voZRDnoIrZPqlo3DPiI4y9lwg/jqx+1Om94/W6ZaPDOUbnjOt/99w66zk+l1Xg==" + }, + "cookie-signature": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", + "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" + }, + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "requires": { + "ms": "2.0.0" + } + }, + "depd": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", + "integrity": "sha1-m81S4UwJd2PnSbJ0xDRu0uVgtak=" + }, + "destroy": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.0.4.tgz", + "integrity": "sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA=" + }, + "dottie": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/dottie/-/dottie-2.0.2.tgz", + "integrity": "sha512-fmrwR04lsniq/uSr8yikThDTrM7epXHBAAjH9TbeH3rEA8tdCO7mRzB9hdmdGyJCxF8KERo9CITcm3kGuoyMhg==" + }, + "ee-first": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", + "integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=" + }, + "encodeurl": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", + "integrity": "sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=" + }, + "escape-html": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", + "integrity": "sha1-Aljq5NPQwJdN4cFpGI7wBR0dGYg=" + }, + "etag": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", + "integrity": "sha1-Qa4u62XvpiJorr/qg6x9eSmbCIc=" + }, + "express": { + "version": "4.17.1", + "resolved": "https://registry.npmjs.org/express/-/express-4.17.1.tgz", + "integrity": "sha512-mHJ9O79RqluphRrcw2X/GTh3k9tVv8YcoyY4Kkh4WDMUYKRZUq0h1o0w2rrrxBqM7VoeUVqgb27xlEMXTnYt4g==", + "requires": { + "accepts": "~1.3.7", + "array-flatten": "1.1.1", + "body-parser": "1.19.0", + "content-disposition": "0.5.3", + "content-type": "~1.0.4", + "cookie": "0.4.0", + "cookie-signature": "1.0.6", + "debug": "2.6.9", + "depd": "~1.1.2", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "finalhandler": "~1.1.2", + "fresh": "0.5.2", + "merge-descriptors": "1.0.1", + "methods": "~1.1.2", + "on-finished": "~2.3.0", + "parseurl": "~1.3.3", + "path-to-regexp": "0.1.7", + "proxy-addr": "~2.0.5", + "qs": "6.7.0", + "range-parser": "~1.2.1", + "safe-buffer": "5.1.2", + "send": "0.17.1", + "serve-static": "1.14.1", + "setprototypeof": "1.1.1", + "statuses": "~1.5.0", + "type-is": "~1.6.18", + "utils-merge": "1.0.1", + "vary": "~1.1.2" + } + }, + "finalhandler": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.2.tgz", + "integrity": "sha512-aAWcW57uxVNrQZqFXjITpW3sIUQmHGG3qSb9mUah9MgMC4NeWhNOlNjXEYq3HjRAvL6arUviZGGJsBg6z0zsWA==", + "requires": { + "debug": "2.6.9", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "on-finished": "~2.3.0", + "parseurl": "~1.3.3", + "statuses": "~1.5.0", + "unpipe": "~1.0.0" + } + }, + "forwarded": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.1.2.tgz", + "integrity": "sha1-mMI9qxF1ZXuMBXPozszZGw/xjIQ=" + }, + "fresh": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", + "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=" + }, + "http-errors": { + "version": "1.7.2", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.7.2.tgz", + "integrity": "sha512-uUQBt3H/cSIVfch6i1EuPNy/YsRSOUBXTVfZ+yR7Zjez3qjBz6i9+i4zjNaoqcoFVI4lQJ5plg63TvGfRSDCRg==", + "requires": { + "depd": "~1.1.2", + "inherits": "2.0.3", + "setprototypeof": "1.1.1", + "statuses": ">= 1.5.0 < 2", + "toidentifier": "1.0.0" + } + }, + "iconv-lite": { + "version": "0.4.24", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", + "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", + "requires": { + "safer-buffer": ">= 2.1.2 < 3" + } + }, + "inflection": { + "version": "1.12.0", + "resolved": "https://registry.npmjs.org/inflection/-/inflection-1.12.0.tgz", + "integrity": "sha1-ogCTVlbW9fa8TcdQLhrstwMihBY=" + }, + "inherits": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", + "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" + }, + "ipaddr.js": { + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", + "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==" + }, + "lodash": { + "version": "4.17.20", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.20.tgz", + "integrity": "sha512-PlhdFcillOINfeV7Ni6oF1TAEayyZBoZ8bcshTHqOYJYlrqzRK5hagpagky5o4HfCzzd1TRkXPMFq6cKk9rGmA==" + }, + "media-typer": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", + "integrity": "sha1-hxDXrwqmJvj/+hzgAWhUUmMlV0g=" + }, + "merge-descriptors": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", + "integrity": "sha1-sAqqVW3YtEVoFQ7J0blT8/kMu2E=" + }, + "methods": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", + "integrity": "sha1-VSmk1nZUE07cxSZmVoNbD4Ua/O4=" + }, + "mime": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", + "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==" + }, + "mime-db": { + "version": "1.44.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.44.0.tgz", + "integrity": "sha512-/NOTfLrsPBVeH7YtFPgsVWveuL+4SjjYxaQ1xtM1KMFj7HdxlBlxeyNLzhyJVx7r4rZGJAZ/6lkKCitSc/Nmpg==" + }, + "mime-types": { + "version": "2.1.27", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.27.tgz", + "integrity": "sha512-JIhqnCasI9yD+SsmkquHBxTSEuZdQX5BuQnS2Vc7puQQQ+8yiP5AY5uWhpdv4YL4VM5c6iliiYWPgJ/nJQLp7w==", + "requires": { + "mime-db": "1.44.0" + } + }, + "moment": { + "version": "2.29.1", + "resolved": "https://registry.npmjs.org/moment/-/moment-2.29.1.tgz", + "integrity": "sha512-kHmoybcPV8Sqy59DwNDY3Jefr64lK/by/da0ViFcuA4DH0vQg5Q6Ze5VimxkfQNSC+Mls/Kx53s7TjP1RhFEDQ==" + }, + "moment-timezone": { + "version": "0.5.31", + "resolved": "https://registry.npmjs.org/moment-timezone/-/moment-timezone-0.5.31.tgz", + "integrity": "sha512-+GgHNg8xRhMXfEbv81iDtrVeTcWt0kWmTEY1XQK14dICTXnWJnT0dxdlPspwqF3keKMVPXwayEsk1DI0AA/jdA==", + "requires": { + "moment": ">= 2.9.0" + } + }, + "ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" + }, + "negotiator": { + "version": "0.6.2", + "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.2.tgz", + "integrity": "sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw==" + }, + "on-finished": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.3.0.tgz", + "integrity": "sha1-IPEzZIGwg811M3mSoWlxqi2QaUc=", + "requires": { + "ee-first": "1.1.1" + } + }, + "packet-reader": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/packet-reader/-/packet-reader-1.0.0.tgz", + "integrity": "sha512-HAKu/fG3HpHFO0AA8WE8q2g+gBJaZ9MG7fcKk+IJPLTGAD6Psw4443l+9DGRbOIh3/aXr7Phy0TjilYivJo5XQ==" + }, + "parseurl": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", + "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==" + }, + "path-to-regexp": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", + "integrity": "sha1-32BBeABfUi8V60SQ5yR6G/qmf4w=" + }, + "pg": { + "version": "8.4.1", + "resolved": "https://registry.npmjs.org/pg/-/pg-8.4.1.tgz", + "integrity": "sha512-NRsH0aGMXmX1z8Dd0iaPCxWUw4ffu+lIAmGm+sTCwuDDWkpEgRCAHZYDwqaNhC5hG5DRMOjSUFasMWhvcmLN1A==", + "requires": { + "buffer-writer": "2.0.0", + "packet-reader": "1.0.0", + "pg-connection-string": "^2.4.0", + "pg-pool": "^3.2.1", + "pg-protocol": "^1.3.0", + "pg-types": "^2.1.0", + "pgpass": "1.x" + } + }, + "pg-connection-string": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/pg-connection-string/-/pg-connection-string-2.4.0.tgz", + "integrity": "sha512-3iBXuv7XKvxeMrIgym7njT+HlZkwZqqGX4Bu9cci8xHZNT+Um1gWKqCsAzcC0d95rcKMU5WBg6YRUcHyV0HZKQ==" + }, + "pg-int8": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/pg-int8/-/pg-int8-1.0.1.tgz", + "integrity": "sha512-WCtabS6t3c8SkpDBUlb1kjOs7l66xsGdKpIPZsg4wR+B3+u9UAum2odSsF9tnvxg80h4ZxLWMy4pRjOsFIqQpw==" + }, + "pg-pool": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/pg-pool/-/pg-pool-3.2.1.tgz", + "integrity": "sha512-BQDPWUeKenVrMMDN9opfns/kZo4lxmSWhIqo+cSAF7+lfi9ZclQbr9vfnlNaPr8wYF3UYjm5X0yPAhbcgqNOdA==" + }, + "pg-protocol": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/pg-protocol/-/pg-protocol-1.3.0.tgz", + "integrity": "sha512-64/bYByMrhWULUaCd+6/72c9PMWhiVFs3EVxl9Ct6a3v/U8+rKgqP2w+kKg/BIGgMJyB+Bk/eNivT32Al+Jghw==" + }, + "pg-types": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/pg-types/-/pg-types-2.2.0.tgz", + "integrity": "sha512-qTAAlrEsl8s4OiEQY69wDvcMIdQN6wdz5ojQiOy6YRMuynxenON0O5oCpJI6lshc6scgAY8qvJ2On/p+CXY0GA==", + "requires": { + "pg-int8": "1.0.1", + "postgres-array": "~2.0.0", + "postgres-bytea": "~1.0.0", + "postgres-date": "~1.0.4", + "postgres-interval": "^1.1.0" + } + }, + "pgpass": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/pgpass/-/pgpass-1.0.4.tgz", + "integrity": "sha512-YmuA56alyBq7M59vxVBfPJrGSozru8QAdoNlWuW3cz8l+UX3cWge0vTvjKhsSHSJpo3Bom8/Mm6hf0TR5GY0+w==", + "requires": { + "split2": "^3.1.1" + } + }, + "postgres-array": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/postgres-array/-/postgres-array-2.0.0.tgz", + "integrity": "sha512-VpZrUqU5A69eQyW2c5CA1jtLecCsN2U/bD6VilrFDWq5+5UIEVO7nazS3TEcHf1zuPYO/sqGvUvW62g86RXZuA==" + }, + "postgres-bytea": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/postgres-bytea/-/postgres-bytea-1.0.0.tgz", + "integrity": "sha1-AntTPAqokOJtFy1Hz5zOzFIazTU=" + }, + "postgres-date": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/postgres-date/-/postgres-date-1.0.7.tgz", + "integrity": "sha512-suDmjLVQg78nMK2UZ454hAG+OAW+HQPZ6n++TNDUX+L0+uUlLywnoxJKDou51Zm+zTCjrCl0Nq6J9C5hP9vK/Q==" + }, + "postgres-interval": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/postgres-interval/-/postgres-interval-1.2.0.tgz", + "integrity": "sha512-9ZhXKM/rw350N1ovuWHbGxnGh/SNJ4cnxHiM0rxE4VN41wsg8P8zWn9hv/buK00RP4WvlOyr/RBDiptyxVbkZQ==", + "requires": { + "xtend": "^4.0.0" + } + }, + "proxy-addr": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.6.tgz", + "integrity": "sha512-dh/frvCBVmSsDYzw6n926jv974gddhkFPfiN8hPOi30Wax25QZyZEGveluCgliBnqmuM+UJmBErbAUFIoDbjOw==", + "requires": { + "forwarded": "~0.1.2", + "ipaddr.js": "1.9.1" + } + }, + "qs": { + "version": "6.7.0", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.7.0.tgz", + "integrity": "sha512-VCdBRNFTX1fyE7Nb6FYoURo/SPe62QCaAyzJvUjwRaIsc+NePBEniHlvxFmmX56+HZphIGtV0XeCirBtpDrTyQ==" + }, + "range-parser": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", + "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==" + }, + "raw-body": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.4.0.tgz", + "integrity": "sha512-4Oz8DUIwdvoa5qMJelxipzi/iJIi40O5cGV1wNYp5hvZP8ZN0T+jiNkL0QepXs+EsQ9XJ8ipEDoiH70ySUJP3Q==", + "requires": { + "bytes": "3.1.0", + "http-errors": "1.7.2", + "iconv-lite": "0.4.24", + "unpipe": "1.0.0" + } + }, + "readable-stream": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", + "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", + "requires": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + } + }, + "retry-as-promised": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/retry-as-promised/-/retry-as-promised-3.2.0.tgz", + "integrity": "sha512-CybGs60B7oYU/qSQ6kuaFmRd9sTZ6oXSc0toqePvV74Ac6/IFZSI1ReFQmtCN+uvW1Mtqdwpvt/LGOiCBAY2Mg==", + "requires": { + "any-promise": "^1.3.0" + } + }, + "safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==" + }, + "safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" + }, + "semver": { + "version": "7.3.2", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.2.tgz", + "integrity": "sha512-OrOb32TeeambH6UrhtShmF7CRDqhL6/5XpPNp2DuRH6+9QLw/orhp72j87v8Qa1ScDkvrrBNpZcDejAirJmfXQ==" + }, + "send": { + "version": "0.17.1", + "resolved": "https://registry.npmjs.org/send/-/send-0.17.1.tgz", + "integrity": "sha512-BsVKsiGcQMFwT8UxypobUKyv7irCNRHk1T0G680vk88yf6LBByGcZJOTJCrTP2xVN6yI+XjPJcNuE3V4fT9sAg==", + "requires": { + "debug": "2.6.9", + "depd": "~1.1.2", + "destroy": "~1.0.4", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "fresh": "0.5.2", + "http-errors": "~1.7.2", + "mime": "1.6.0", + "ms": "2.1.1", + "on-finished": "~2.3.0", + "range-parser": "~1.2.1", + "statuses": "~1.5.0" + }, + "dependencies": { + "ms": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.1.tgz", + "integrity": "sha512-tgp+dl5cGk28utYktBsrFqA7HKgrhgPsg6Z/EfhWI4gl1Hwq8B/GmY/0oXZ6nF8hDVesS/FpnYaD/kOWhYQvyg==" + } + } + }, + "sequelize": { + "version": "6.3.5", + "resolved": "https://registry.npmjs.org/sequelize/-/sequelize-6.3.5.tgz", + "integrity": "sha512-MiwiPkYSA8NWttRKAXdU9h0TxP6HAc1fl7qZmMO/VQqQOND83G4nZLXd0kWILtAoT9cxtZgFqeb/MPYgEeXwsw==", + "requires": { + "debug": "^4.1.1", + "dottie": "^2.0.0", + "inflection": "1.12.0", + "lodash": "^4.17.15", + "moment": "^2.26.0", + "moment-timezone": "^0.5.31", + "retry-as-promised": "^3.2.0", + "semver": "^7.3.2", + "sequelize-pool": "^6.0.0", + "toposort-class": "^1.0.1", + "uuid": "^8.1.0", + "validator": "^10.11.0", + "wkx": "^0.5.0" + }, + "dependencies": { + "debug": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.2.0.tgz", + "integrity": "sha512-IX2ncY78vDTjZMFUdmsvIRFY2Cf4FnD0wRs+nQwJU8Lu99/tPFdb0VybiiMTPe3I6rQmwsqQqRBvxU+bZ/I8sg==", + "requires": { + "ms": "2.1.2" + } + }, + "ms": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" + } + } + }, + "sequelize-pool": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/sequelize-pool/-/sequelize-pool-6.1.0.tgz", + "integrity": "sha512-4YwEw3ZgK/tY/so+GfnSgXkdwIJJ1I32uZJztIEgZeAO6HMgj64OzySbWLgxj+tXhZCJnzRfkY9gINw8Ft8ZMg==" + }, + "serve-static": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.14.1.tgz", + "integrity": "sha512-JMrvUwE54emCYWlTI+hGrGv5I8dEwmco/00EvkzIIsR7MqrHonbD9pO2MOfFnpFntl7ecpZs+3mW+XbQZu9QCg==", + "requires": { + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "parseurl": "~1.3.3", + "send": "0.17.1" + } + }, + "setprototypeof": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.1.tgz", + "integrity": "sha512-JvdAWfbXeIGaZ9cILp38HntZSFSo3mWg6xGcJJsd+d4aRMOqauag1C63dJfDw7OaMYwEbHMOxEZ1lqVRYP2OAw==" + }, + "split2": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/split2/-/split2-3.2.2.tgz", + "integrity": "sha512-9NThjpgZnifTkJpzTZ7Eue85S49QwpNhZTq6GRJwObb6jnLFNGB7Qm73V5HewTROPyxD0C29xqmaI68bQtV+hg==", + "requires": { + "readable-stream": "^3.0.0" + } + }, + "statuses": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", + "integrity": "sha1-Fhx9rBd2Wf2YEfQ3cfqZOBR4Yow=" + }, + "string_decoder": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", + "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", + "requires": { + "safe-buffer": "~5.2.0" + }, + "dependencies": { + "safe-buffer": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", + "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==" + } + } + }, + "toidentifier": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.0.tgz", + "integrity": "sha512-yaOH/Pk/VEhBWWTlhI+qXxDFXlejDGcQipMlyxda9nthulaxLZUNcUqFxokp0vcYnvteJln5FNQDRrxj3YcbVw==" + }, + "toposort-class": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/toposort-class/-/toposort-class-1.0.1.tgz", + "integrity": "sha1-f/0feMi+KMO6Rc1OGj9e4ZO9mYg=" + }, + "type-is": { + "version": "1.6.18", + "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", + "integrity": "sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==", + "requires": { + "media-typer": "0.3.0", + "mime-types": "~2.1.24" + } + }, + "unpipe": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", + "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=" + }, + "util-deprecate": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", + "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=" + }, + "utils-merge": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", + "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=" + }, + "uuid": { + "version": "8.3.1", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.1.tgz", + "integrity": "sha512-FOmRr+FmWEIG8uhZv6C2bTgEVXsHk08kE7mPlrBbEe+c3r9pjceVPgupIfNIhc4yx55H69OXANrUaSuu9eInKg==" + }, + "validator": { + "version": "10.11.0", + "resolved": "https://registry.npmjs.org/validator/-/validator-10.11.0.tgz", + "integrity": "sha512-X/p3UZerAIsbBfN/IwahhYaBbY68EN/UQBWHtsbXGT5bfrH/p4NQzUCG1kF/rtKaNpnJ7jAu6NGTdSNtyNIXMw==" + }, + "vary": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", + "integrity": "sha1-IpnwLG3tMNSllhsLn3RSShj2NPw=" + }, + "wkx": { + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/wkx/-/wkx-0.5.0.tgz", + "integrity": "sha512-Xng/d4Ichh8uN4l0FToV/258EjMGU9MGcA0HV2d9B/ZpZB3lqQm7nkOdZdm5GhKtLLhAE7PiVQwN4eN+2YJJUg==", + "requires": { + "@types/node": "*" + } + }, + "xtend": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", + "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==" + } + } +} diff --git a/package.json b/package.json new file mode 100644 index 0000000..cf235d7 --- /dev/null +++ b/package.json @@ -0,0 +1,26 @@ +{ + "name": "fancytodo", + "version": "1.0.0", + "description": "Todo App", + "main": "app.js", + "scripts": { + "test": "echo \"Error: no test specified\" && exit 1", + "dev": "nodemon app.js" + }, + "repository": { + "type": "git", + "url": "git+https://github.com/torianyap/FancyTodo.git" + }, + "keywords": [], + "author": "torianyap", + "license": "ISC", + "bugs": { + "url": "https://github.com/torianyap/FancyTodo/issues" + }, + "homepage": "https://github.com/torianyap/FancyTodo#readme", + "dependencies": { + "express": "^4.17.1", + "pg": "^8.4.1", + "sequelize": "^6.3.5" + } +} diff --git a/server/readme.md b/server/readme.md index 3aadcc2..a5b0f4a 100644 --- a/server/readme.md +++ b/server/readme.md @@ -1 +1 @@ -# FancyTodo Server \ No newline at end of file +# FancyTodoServer \ No newline at end of file From 5161abe0ac0be3078091798a54d6d0f7bb2f163e Mon Sep 17 00:00:00 2001 From: torianyap Date: Mon, 26 Oct 2020 12:21:09 +0700 Subject: [PATCH 02/22] mau liat gimana jadinya --- README.md | 69 +++++++++++++++++++++++++++++++++++++++++++++---------- 1 file changed, 57 insertions(+), 12 deletions(-) diff --git a/README.md b/README.md index af5b9fa..3b3b342 100644 --- a/README.md +++ b/README.md @@ -1,8 +1,38 @@ # FancyTodo -**Show List Todo** +**Create Todo** ---- - Return JSON data about all todos + Returns JSON data from new todo + +* **URL** + + /todos + +* **Method:** + + `POST` + +* **Data Params** + + {ntar lah} + +* **Success Response:** + + * **Code:** 201
+ **Content:** `{id: 1, title: 'study', description: 'learn VSCode', status: false, due_date: date}` + +* **Error Response:** + * **Code:** 400
+ **Content:** `{validation errors}` + + OR + + * **Code:** 500
+ **Content:** `error` + +**Read Todo** +---- + Returns JSON data about all todos * **URL** @@ -15,22 +45,37 @@ * **Success Response:** * **Code:** 200
- **Content:** `{ id : 12 }` + **Content:** `[{id: 1, title: 'study', description: 'learn VSCode', status: false, due_date: date}, ...]` * **Error Response:** - * **Code:** 401 UNAUTHORIZED
- **Content:** `{ error : "Log in" }` + * **Code:** 500
+ **Content:** `error` + +**Get todo by ID** +---- + Returns JSON data about a single todo + +* **URL** + + /todos/:id - OR +* **Method:** - * **Code:** 422 UNPROCESSABLE ENTRY
- **Content:** `{ error : "Email Invalid" }` + `GET` + +* **URL Params** -* **Sample Call:** + **Required:** + + `id=[integer]` - <_Just a sample call to your endpoint in a runnable format ($.ajax call or a curl request) - this makes life easier and more predictable._> +* **Success Response:** -* **Notes:** + * **Code:** 200
+ **Content:** `{id: 1, title: 'study', description: 'learn VSCode', status: false, due_date: date}` + +* **Error Response:** - <_This is where all uncertainties, commentary, discussion etc. can go. I recommend timestamping and identifying oneself when leaving comments here._> \ No newline at end of file + * **Code:** 404
+ **Content:** `{ error }` \ No newline at end of file From 8e7a84490e92db62e1f26925b8951768002032da Mon Sep 17 00:00:00 2001 From: torianyap Date: Mon, 26 Oct 2020 12:40:15 +0700 Subject: [PATCH 03/22] test 2 --- README.md | 14 ++++++++++++-- server/app.js | 9 +++++++++ server/config/config.json | 23 +++++++++++++++++++++++ server/models/index.js | 37 +++++++++++++++++++++++++++++++++++++ server/readme.md | 1 - 5 files changed, 81 insertions(+), 3 deletions(-) create mode 100644 server/app.js create mode 100644 server/config/config.json create mode 100644 server/models/index.js delete mode 100644 server/readme.md diff --git a/README.md b/README.md index 3b3b342..7edd1bf 100644 --- a/README.md +++ b/README.md @@ -14,12 +14,22 @@ * **Data Params** - {ntar lah} + { + title: 'learn REST API', + description: 'learn how to create RESTful API with Express and Sequelize', + due_date: '2020-10-31' + } * **Success Response:** * **Code:** 201
- **Content:** `{id: 1, title: 'study', description: 'learn VSCode', status: false, due_date: date}` + **Content:** { + id: 1, + title: 'study', + description: 'learn VSCode', + status: false, + due_date: '2020-10-31' + }` * **Error Response:** * **Code:** 400
diff --git a/server/app.js b/server/app.js new file mode 100644 index 0000000..767e90f --- /dev/null +++ b/server/app.js @@ -0,0 +1,9 @@ +const express = require('express') +const router = require('./routes') +const app = express() +const port = 3000 + +app.use(router) +app.use(express.urlencoded({extended: true})) + +app.listen(port, () => console.log(`listening at ${port}`)) \ No newline at end of file diff --git a/server/config/config.json b/server/config/config.json new file mode 100644 index 0000000..975560e --- /dev/null +++ b/server/config/config.json @@ -0,0 +1,23 @@ +{ + "development": { + "username": "postgres", + "password": "torian05092002", + "database": "fancytodo", + "host": "127.0.0.1", + "dialect": "postgres" + }, + "test": { + "username": "root", + "password": null, + "database": "database_test", + "host": "127.0.0.1", + "dialect": "mysql" + }, + "production": { + "username": "root", + "password": null, + "database": "database_production", + "host": "127.0.0.1", + "dialect": "mysql" + } +} diff --git a/server/models/index.js b/server/models/index.js new file mode 100644 index 0000000..33f09e7 --- /dev/null +++ b/server/models/index.js @@ -0,0 +1,37 @@ +'use strict'; + +const fs = require('fs'); +const path = require('path'); +const Sequelize = require('sequelize'); +const basename = path.basename(__filename); +const env = process.env.NODE_ENV || 'development'; +const config = require(__dirname + '/../config/config.json')[env]; +const db = {}; + +let sequelize; +if (config.use_env_variable) { + sequelize = new Sequelize(process.env[config.use_env_variable], config); +} else { + sequelize = new Sequelize(config.database, config.username, config.password, config); +} + +fs + .readdirSync(__dirname) + .filter(file => { + return (file.indexOf('.') !== 0) && (file !== basename) && (file.slice(-3) === '.js'); + }) + .forEach(file => { + const model = require(path.join(__dirname, file))(sequelize, Sequelize.DataTypes); + db[model.name] = model; + }); + +Object.keys(db).forEach(modelName => { + if (db[modelName].associate) { + db[modelName].associate(db); + } +}); + +db.sequelize = sequelize; +db.Sequelize = Sequelize; + +module.exports = db; diff --git a/server/readme.md b/server/readme.md deleted file mode 100644 index a5b0f4a..0000000 --- a/server/readme.md +++ /dev/null @@ -1 +0,0 @@ -# FancyTodoServer \ No newline at end of file From 76166a59cf67711db831ac3467d7c5a2d793f2db Mon Sep 17 00:00:00 2001 From: torianyap Date: Mon, 26 Oct 2020 14:52:01 +0700 Subject: [PATCH 04/22] rest api --- server/app.js | 9 -- server/controllers/todoController.js | 84 +++++++++++++++++++ .../migrations/20201026060655-create-to-do.js | 36 ++++++++ server/models/todo.js | 40 +++++++++ server/routes/index.js | 6 ++ server/routes/todoRoute.js | 11 +++ 6 files changed, 177 insertions(+), 9 deletions(-) delete mode 100644 server/app.js create mode 100644 server/controllers/todoController.js create mode 100644 server/migrations/20201026060655-create-to-do.js create mode 100644 server/models/todo.js create mode 100644 server/routes/index.js create mode 100644 server/routes/todoRoute.js diff --git a/server/app.js b/server/app.js deleted file mode 100644 index 767e90f..0000000 --- a/server/app.js +++ /dev/null @@ -1,9 +0,0 @@ -const express = require('express') -const router = require('./routes') -const app = express() -const port = 3000 - -app.use(router) -app.use(express.urlencoded({extended: true})) - -app.listen(port, () => console.log(`listening at ${port}`)) \ No newline at end of file diff --git a/server/controllers/todoController.js b/server/controllers/todoController.js new file mode 100644 index 0000000..712aaa1 --- /dev/null +++ b/server/controllers/todoController.js @@ -0,0 +1,84 @@ +const {ToDo} = require('../models/index') + +class ToDoController { + static async create(req, res) { + try { + const {title, description, due_date} = req.body + + const newToDo = await ToDo.create({title, description, due_date}, {returning: true}) + res.status(200).json(newToDo) + } catch (error) { + res.status(500).json(error) + } + } + + static async read(req, res) { + try { + const todos = await ToDo.findAll({order: [['id', 'asc']]}) + res.status(200).json(todos) + } catch (error) { + res.status(500).json(error) + } + } + + static async findOne(req, res) { + try { + const id = +req.params.id + const todo = await ToDo.findByPk(id) + if (todo) { + res.status(200).json(todo) + } else { + throw new Error(`id ${+req.params.id} is not found`) + } + } catch (error) { + res.status(500).json(error) + } + } + + static async update(req, res) { + try { + const id = +req.params.id + const {title, description, due_date} = req.body + + const updated = await ToDo.update( + {title, description, due_date}, + {where: {id: id}, returning: true} + ) + + res.status(200).json(updated[1][0]) + + } catch (error) { + res.status(500).json(error) + } + } + + static async finish(req, res) { + try { + const finished = await ToDo.update({status: true}, { + where: { + id: +req.params.id + }, + returning: true + }) + res.status(200).json(finished[1][0]) + } catch (error) { + res.status(500).json(error) + } + } + + static async delete(req, res) { + try { + await ToDo.destroy({ + where: { + id: +req.params.id + } + }) + res.status(200).json({msg: `todo deleted successfuly`}) + } catch (error) { + res.status(500).json(error) + } + + } +} + +module.exports = ToDoController \ No newline at end of file diff --git a/server/migrations/20201026060655-create-to-do.js b/server/migrations/20201026060655-create-to-do.js new file mode 100644 index 0000000..89086b5 --- /dev/null +++ b/server/migrations/20201026060655-create-to-do.js @@ -0,0 +1,36 @@ +'use strict'; +module.exports = { + up: async (queryInterface, Sequelize) => { + await queryInterface.createTable('ToDos', { + id: { + allowNull: false, + autoIncrement: true, + primaryKey: true, + type: Sequelize.INTEGER + }, + title: { + type: Sequelize.STRING + }, + description: { + type: Sequelize.STRING + }, + status: { + type: Sequelize.BOOLEAN + }, + due_date: { + type: Sequelize.DATE + }, + createdAt: { + allowNull: false, + type: Sequelize.DATE + }, + updatedAt: { + allowNull: false, + type: Sequelize.DATE + } + }); + }, + down: async (queryInterface, Sequelize) => { + await queryInterface.dropTable('ToDos'); + } +}; \ No newline at end of file diff --git a/server/models/todo.js b/server/models/todo.js new file mode 100644 index 0000000..223724d --- /dev/null +++ b/server/models/todo.js @@ -0,0 +1,40 @@ +'use strict'; +const {Model} = require('sequelize'); + +module.exports = (sequelize, DataTypes) => { + class ToDo extends Model { + /** + * Helper method for defining associations. + * This method is not a part of Sequelize lifecycle. + * The `models/index` file will call this method automatically. + */ + static associate(models) { + // define association here + } + }; + ToDo.init({ + title: DataTypes.STRING, + description: DataTypes.STRING, + status: DataTypes.BOOLEAN, + due_date: { + type: DataTypes.DATE, + validate: { + costum(value) { + const now = new Date() + if (now >= value) { + throw new Error('due date should be greater than today') + } + } + } + } + }, { + sequelize, + modelName: 'ToDo', + }); + + ToDo.addHook('beforeCreate', (instance, options) => { + instance.status = false + }) + + return ToDo; +}; \ No newline at end of file diff --git a/server/routes/index.js b/server/routes/index.js new file mode 100644 index 0000000..f28c3da --- /dev/null +++ b/server/routes/index.js @@ -0,0 +1,6 @@ +const route = require('express').Router() +const todoRoute = require('./todoRoute') + +route.use('/todos', todoRoute) + +module.exports = route \ No newline at end of file diff --git a/server/routes/todoRoute.js b/server/routes/todoRoute.js new file mode 100644 index 0000000..b3332fc --- /dev/null +++ b/server/routes/todoRoute.js @@ -0,0 +1,11 @@ +const route = require('express').Router() +const ToDoController = require('../controllers/todoController') + +route.post('/', ToDoController.create) +route.get('/', ToDoController.read) +route.get('/:id', ToDoController.findOne) +route.put('/:id', ToDoController.update) +route.patch('/:id', ToDoController.finish) +route.delete('/:id', ToDoController.delete) + +module.exports = route \ No newline at end of file From 3195b57f55b38f344c5de6b91dc1b1f3088a290a Mon Sep 17 00:00:00 2001 From: torianyap Date: Mon, 26 Oct 2020 14:52:17 +0700 Subject: [PATCH 05/22] rest api --- README.md | 145 ++++++++++++++++++++++++++++++++++++++++++++++++------ app.js | 9 ++++ 2 files changed, 138 insertions(+), 16 deletions(-) create mode 100644 app.js diff --git a/README.md b/README.md index 7edd1bf..36ac5cd 100644 --- a/README.md +++ b/README.md @@ -14,22 +14,12 @@ * **Data Params** - { - title: 'learn REST API', - description: 'learn how to create RESTful API with Express and Sequelize', - due_date: '2020-10-31' - } + `{title: 'study', description: 'learn REST API', due_date: '2020-10-31'}` * **Success Response:** * **Code:** 201
- **Content:** { - id: 1, - title: 'study', - description: 'learn VSCode', - status: false, - due_date: '2020-10-31' - }` + **Content:** `{id: 1, title: 'study', description: 'learn REST API', status: false, due_date: '2020-10-31'}` * **Error Response:** * **Code:** 400
@@ -38,7 +28,9 @@ OR * **Code:** 500
- **Content:** `error` + **Content:** `{ error }` + +
**Read Todo** ---- @@ -60,8 +52,10 @@ * **Error Response:** * **Code:** 500
- **Content:** `error` + **Content:** `{ error }` +
+ **Get todo by ID** ---- Returns JSON data about a single todo @@ -83,9 +77,128 @@ * **Success Response:** * **Code:** 200
- **Content:** `{id: 1, title: 'study', description: 'learn VSCode', status: false, due_date: date}` + **Content:** `{id: 1, title: 'study', description: 'learn VSCode', status: false, due_date: '2020-10-31'}` * **Error Response:** * **Code:** 404
- **Content:** `{ error }` \ No newline at end of file + **Content:** `{ error not found }` + + OR + + * **Code:** 500
+ **Content:** `{ error }` + +
+ +**Update todo by ID** +---- + Returns JSON data about updated todo + +* **URL** + + /todos/:id + +* **Method:** + + `PUT` + +* **URL Params** + + **Required:** + + `id=[integer]` + +* **Data Params** + + `{title: 'study', description: 'learn REST API', status: false, due_date: '2020-10-31'}` + +* **Success Response:** + + * **Code:** 200
+ **Content:** `{id: 1, title: 'study', description: 'learn VSCode', status: false, due_date: '2020-10-31'}` + +* **Error Response:** + + * **Code:** 404
+ **Content:** `{ error not found }` + + OR + + * **Code:** 500
+ **Content:** `{ error }` + +
+ +**Update todo status by ID** +---- + Returns JSON data about updated todo + +* **URL** + + /todos/:id + +* **Method:** + + `PATCH` + +* **URL Params** + + **Required:** + + `id=[integer]` + +* **Success Response:** + + * **Code:** 200
+ **Content:** `{id: 1, title: 'study', description: 'learn VSCode', status: true, due_date: '2020-10-31'}` + +* **Error Response:** + + * **Code:** 400
+ **Content:** `{ validation errors }` + + OR + + * **Code:** 404
+ **Content:** `{ error not found }` + + OR + + * **Code:** 500
+ **Content:** `{ error }` + +
+ +**Delete Todo by ID** +---- + Returns message + +* **URL** + + /todos/:id + +* **Method:** + + `DELETE` + +* **URL Params** + + **Required:** + + `id=[integer]` + +* **Success Response:** + + * **Code:** 200
+ **Content:** `{message: 'todo deleted successfuly'}` + +* **Error Response:** + + * **Code:** 404
+ **Content:** `{ error not found }` + + OR + + * **Code:** 500
+ **Content:** `{ error }` \ No newline at end of file diff --git a/app.js b/app.js new file mode 100644 index 0000000..0e23994 --- /dev/null +++ b/app.js @@ -0,0 +1,9 @@ +const express = require('express') +const router = require('./server/routes') +const app = express() +const port = 3000 + +app.use(express.urlencoded({extended: true})) +app.use(router) + +app.listen(port, () => console.log(`listening at ${port}`)) \ No newline at end of file From 022a0592d35dc996129a723f6ff10dce20d840be Mon Sep 17 00:00:00 2001 From: torianyap Date: Mon, 26 Oct 2020 17:55:43 +0700 Subject: [PATCH 06/22] day1 --- .env | 3 + README.md | 3 + app.js | 5 +- package-lock.json | 567 +++++++++++++++++- package.json | 5 + server/controllers/todoController.js | 70 ++- server/controllers/userController.js | 55 ++ server/helper/bcrypt.js | 16 + server/helper/jwt.js | 10 + .../migrations/20201026094340-create-user.js | 30 + server/models/user.js | 35 ++ server/routes/index.js | 2 + server/routes/userRoute.js | 7 + 13 files changed, 786 insertions(+), 22 deletions(-) create mode 100644 .env create mode 100644 server/controllers/userController.js create mode 100644 server/helper/bcrypt.js create mode 100644 server/helper/jwt.js create mode 100644 server/migrations/20201026094340-create-user.js create mode 100644 server/models/user.js create mode 100644 server/routes/userRoute.js diff --git a/.env b/.env new file mode 100644 index 0000000..01b4f08 --- /dev/null +++ b/.env @@ -0,0 +1,3 @@ +SALT=10 +SECRET=redpanda +PORT=3000 \ No newline at end of file diff --git a/README.md b/README.md index 36ac5cd..f8b0fc1 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,8 @@ # FancyTodo +**Run** +npm run dev + **Create Todo** ---- Returns JSON data from new todo diff --git a/app.js b/app.js index 0e23994..eee1226 100644 --- a/app.js +++ b/app.js @@ -1,8 +1,11 @@ +require('dotenv').config() + const express = require('express') const router = require('./server/routes') const app = express() -const port = 3000 +const port = process.env.PORT +app.use(express.json()) app.use(express.urlencoded({extended: true})) app.use(router) diff --git a/package-lock.json b/package-lock.json index 401eeec..d9717ff 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,5 +1,5 @@ { - "name": "FancyTodo", + "name": "fancytodo", "version": "1.0.0", "lockfileVersion": 1, "requires": true, @@ -9,6 +9,11 @@ "resolved": "https://registry.npmjs.org/@types/node/-/node-14.14.3.tgz", "integrity": "sha512-33/L34xS7HVUx23e0wOT2V1qPF1IrHgQccdJVm9uXGTB9vFBrrzBtkQymT8VskeKOxjz55MSqMv0xuLq+u98WQ==" }, + "abbrev": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz", + "integrity": "sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==" + }, "accepts": { "version": "1.3.7", "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.7.tgz", @@ -18,16 +23,73 @@ "negotiator": "0.6.2" } }, + "ansi-regex": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", + "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=" + }, "any-promise": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/any-promise/-/any-promise-1.3.0.tgz", "integrity": "sha1-q8av7tzqUugJzcA3au0845Y10X8=" }, + "aproba": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/aproba/-/aproba-1.2.0.tgz", + "integrity": "sha512-Y9J6ZjXtoYh8RnXVCMOU/ttDmk1aBjunq9vO0ta5x85WDQiQfUF9sIPBITdbiiIVcBo03Hi3jMxigBtsddlXRw==" + }, + "are-we-there-yet": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-1.1.5.tgz", + "integrity": "sha512-5hYdAkZlcG8tOLujVDTgCT+uPX0VnpAH28gWsLfzpXYm7wP6mp5Q/gYyR7YQ0cKVJcXJnl3j2kpBan13PtQf6w==", + "requires": { + "delegates": "^1.0.0", + "readable-stream": "^2.0.6" + }, + "dependencies": { + "readable-stream": { + "version": "2.3.7", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.7.tgz", + "integrity": "sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==", + "requires": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" + } + }, + "string_decoder": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "requires": { + "safe-buffer": "~5.1.0" + } + } + } + }, "array-flatten": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", "integrity": "sha1-ml9pkFGx5wczKPKgCJaLZOopVdI=" }, + "balanced-match": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", + "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" + }, + "bcrypt": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/bcrypt/-/bcrypt-5.0.0.tgz", + "integrity": "sha512-jB0yCBl4W/kVHM2whjfyqnxTmOHkCX4kHEa5nYKSoGeYe8YrjTYTc87/6bwt1g8cmV0QrbhKriETg9jWtcREhg==", + "requires": { + "node-addon-api": "^3.0.0", + "node-pre-gyp": "0.15.0" + } + }, "body-parser": { "version": "1.19.0", "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.19.0.tgz", @@ -45,6 +107,20 @@ "type-is": "~1.6.17" } }, + "brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "requires": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "buffer-equal-constant-time": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz", + "integrity": "sha1-+OcRMvf/5uAaXJaXpMbz5I1cyBk=" + }, "buffer-writer": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/buffer-writer/-/buffer-writer-2.0.0.tgz", @@ -55,6 +131,26 @@ "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.0.tgz", "integrity": "sha512-zauLjrfCG+xvoyaqLoV8bLVXXNGC4JqlxFCutSDWA6fJrTo2ZuvLYTqZ7aHBLZSMOopbzwv8f+wZcVzfVTI2Dg==" }, + "chownr": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.1.4.tgz", + "integrity": "sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg==" + }, + "code-point-at": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", + "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=" + }, + "concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" + }, + "console-control-strings": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/console-control-strings/-/console-control-strings-1.1.0.tgz", + "integrity": "sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4=" + }, "content-disposition": { "version": "0.5.3", "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.3.tgz", @@ -78,6 +174,11 @@ "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" }, + "core-util-is": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", + "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" + }, "debug": { "version": "2.6.9", "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", @@ -86,6 +187,16 @@ "ms": "2.0.0" } }, + "deep-extend": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==" + }, + "delegates": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz", + "integrity": "sha1-hMbhWbgZBP3KWaDvRM2HDTElD5o=" + }, "depd": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", @@ -96,11 +207,30 @@ "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.0.4.tgz", "integrity": "sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA=" }, + "detect-libc": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-1.0.3.tgz", + "integrity": "sha1-+hN8S9aY7fVc1c0CrFWfkaTEups=" + }, + "dotenv": { + "version": "8.2.0", + "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-8.2.0.tgz", + "integrity": "sha512-8sJ78ElpbDJBHNeBzUbUVLsqKdccaa/BXF1uPTw3GrvQTBgrQrtObr2mUrE38vzYd8cEv+m/JBfDLioYcfXoaw==", + "dev": true + }, "dottie": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/dottie/-/dottie-2.0.2.tgz", "integrity": "sha512-fmrwR04lsniq/uSr8yikThDTrM7epXHBAAjH9TbeH3rEA8tdCO7mRzB9hdmdGyJCxF8KERo9CITcm3kGuoyMhg==" }, + "ecdsa-sig-formatter": { + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/ecdsa-sig-formatter/-/ecdsa-sig-formatter-1.0.11.tgz", + "integrity": "sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==", + "requires": { + "safe-buffer": "^5.0.1" + } + }, "ee-first": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", @@ -182,6 +312,52 @@ "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=" }, + "fs-minipass": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/fs-minipass/-/fs-minipass-1.2.7.tgz", + "integrity": "sha512-GWSSJGFy4e9GUeCcbIkED+bgAoFyj7XF1mV8rma3QW4NIqX9Kyx79N/PF61H5udOV3aY1IaMLs6pGbH71nlCTA==", + "requires": { + "minipass": "^2.6.0" + } + }, + "fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" + }, + "gauge": { + "version": "2.7.4", + "resolved": "https://registry.npmjs.org/gauge/-/gauge-2.7.4.tgz", + "integrity": "sha1-LANAXHU4w51+s3sxcCLjJfsBi/c=", + "requires": { + "aproba": "^1.0.3", + "console-control-strings": "^1.0.0", + "has-unicode": "^2.0.0", + "object-assign": "^4.1.0", + "signal-exit": "^3.0.0", + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1", + "wide-align": "^1.1.0" + } + }, + "glob": { + "version": "7.1.6", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.6.tgz", + "integrity": "sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA==", + "requires": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + }, + "has-unicode": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz", + "integrity": "sha1-4Ob+aijPUROIVeCG0Wkedx3iqLk=" + }, "http-errors": { "version": "1.7.2", "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.7.2.tgz", @@ -202,26 +378,144 @@ "safer-buffer": ">= 2.1.2 < 3" } }, + "ignore-walk": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/ignore-walk/-/ignore-walk-3.0.3.tgz", + "integrity": "sha512-m7o6xuOaT1aqheYHKf8W6J5pYH85ZI9w077erOzLje3JsB1gkafkAhHHY19dqjulgIZHFm32Cp5uNZgcQqdJKw==", + "requires": { + "minimatch": "^3.0.4" + } + }, "inflection": { "version": "1.12.0", "resolved": "https://registry.npmjs.org/inflection/-/inflection-1.12.0.tgz", "integrity": "sha1-ogCTVlbW9fa8TcdQLhrstwMihBY=" }, + "inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", + "requires": { + "once": "^1.3.0", + "wrappy": "1" + } + }, "inherits": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" }, + "ini": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.5.tgz", + "integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==" + }, "ipaddr.js": { "version": "1.9.1", "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==" }, + "is-fullwidth-code-point": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", + "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", + "requires": { + "number-is-nan": "^1.0.0" + } + }, + "isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" + }, + "jsonwebtoken": { + "version": "8.5.1", + "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-8.5.1.tgz", + "integrity": "sha512-XjwVfRS6jTMsqYs0EsuJ4LGxXV14zQybNd4L2r0UvbVnSF9Af8x7p5MzbJ90Ioz/9TI41/hTCvznF/loiSzn8w==", + "requires": { + "jws": "^3.2.2", + "lodash.includes": "^4.3.0", + "lodash.isboolean": "^3.0.3", + "lodash.isinteger": "^4.0.4", + "lodash.isnumber": "^3.0.3", + "lodash.isplainobject": "^4.0.6", + "lodash.isstring": "^4.0.1", + "lodash.once": "^4.0.0", + "ms": "^2.1.1", + "semver": "^5.6.0" + }, + "dependencies": { + "ms": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" + }, + "semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==" + } + } + }, + "jwa": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/jwa/-/jwa-1.4.1.tgz", + "integrity": "sha512-qiLX/xhEEFKUAJ6FiBMbes3w9ATzyk5W7Hvzpa/SLYdxNtng+gcurvrI7TbACjIXlsJyr05/S1oUhZrc63evQA==", + "requires": { + "buffer-equal-constant-time": "1.0.1", + "ecdsa-sig-formatter": "1.0.11", + "safe-buffer": "^5.0.1" + } + }, + "jws": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/jws/-/jws-3.2.2.tgz", + "integrity": "sha512-YHlZCB6lMTllWDtSPHz/ZXTsi8S00usEV6v1tjq8tOUZzw7DpSDWVXjXDre6ed1w/pd495ODpHZYSdkRTsa0HA==", + "requires": { + "jwa": "^1.4.1", + "safe-buffer": "^5.0.1" + } + }, "lodash": { "version": "4.17.20", "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.20.tgz", "integrity": "sha512-PlhdFcillOINfeV7Ni6oF1TAEayyZBoZ8bcshTHqOYJYlrqzRK5hagpagky5o4HfCzzd1TRkXPMFq6cKk9rGmA==" }, + "lodash.includes": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/lodash.includes/-/lodash.includes-4.3.0.tgz", + "integrity": "sha1-YLuYqHy5I8aMoeUTJUgzFISfVT8=" + }, + "lodash.isboolean": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/lodash.isboolean/-/lodash.isboolean-3.0.3.tgz", + "integrity": "sha1-bC4XHbKiV82WgC/UOwGyDV9YcPY=" + }, + "lodash.isinteger": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/lodash.isinteger/-/lodash.isinteger-4.0.4.tgz", + "integrity": "sha1-YZwK89A/iwTDH1iChAt3sRzWg0M=" + }, + "lodash.isnumber": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/lodash.isnumber/-/lodash.isnumber-3.0.3.tgz", + "integrity": "sha1-POdoEMWSjQM1IwGsKHMX8RwLH/w=" + }, + "lodash.isplainobject": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", + "integrity": "sha1-fFJqUtibRcRcxpC4gWO+BJf1UMs=" + }, + "lodash.isstring": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/lodash.isstring/-/lodash.isstring-4.0.1.tgz", + "integrity": "sha1-1SfftUVuynzJu5XV2ur4i6VKVFE=" + }, + "lodash.once": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/lodash.once/-/lodash.once-4.1.1.tgz", + "integrity": "sha1-DdOXEhPHxW34gJd9UEyI+0cal6w=" + }, "media-typer": { "version": "0.3.0", "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", @@ -255,6 +549,44 @@ "mime-db": "1.44.0" } }, + "minimatch": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", + "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", + "requires": { + "brace-expansion": "^1.1.7" + } + }, + "minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==" + }, + "minipass": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/minipass/-/minipass-2.9.0.tgz", + "integrity": "sha512-wxfUjg9WebH+CUDX/CdbRlh5SmfZiy/hpkxaRI16Y9W56Pa75sWgd/rvFilSgrauD9NyFymP/+JFV3KwzIsJeg==", + "requires": { + "safe-buffer": "^5.1.2", + "yallist": "^3.0.0" + } + }, + "minizlib": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/minizlib/-/minizlib-1.3.3.tgz", + "integrity": "sha512-6ZYMOEnmVsdCeTJVE0W9ZD+pVnE8h9Hma/iOwwRDsdQoePpoX56/8B6z3P9VNwppJuBKNRuFDRNRqRWexT9G9Q==", + "requires": { + "minipass": "^2.9.0" + } + }, + "mkdirp": { + "version": "0.5.5", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", + "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", + "requires": { + "minimist": "^1.2.5" + } + }, "moment": { "version": "2.29.1", "resolved": "https://registry.npmjs.org/moment/-/moment-2.29.1.tgz", @@ -273,11 +605,118 @@ "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" }, + "needle": { + "version": "2.5.2", + "resolved": "https://registry.npmjs.org/needle/-/needle-2.5.2.tgz", + "integrity": "sha512-LbRIwS9BfkPvNwNHlsA41Q29kL2L/6VaOJ0qisM5lLWsTV3nP15abO5ITL6L81zqFhzjRKDAYjpcBcwM0AVvLQ==", + "requires": { + "debug": "^3.2.6", + "iconv-lite": "^0.4.4", + "sax": "^1.2.4" + }, + "dependencies": { + "debug": { + "version": "3.2.6", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz", + "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==", + "requires": { + "ms": "^2.1.1" + } + }, + "ms": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" + } + } + }, "negotiator": { "version": "0.6.2", "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.2.tgz", "integrity": "sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw==" }, + "node-addon-api": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-3.0.2.tgz", + "integrity": "sha512-+D4s2HCnxPd5PjjI0STKwncjXTUKKqm74MDMz9OPXavjsGmjkvwgLtA5yoxJUdmpj52+2u+RrXgPipahKczMKg==" + }, + "node-pre-gyp": { + "version": "0.15.0", + "resolved": "https://registry.npmjs.org/node-pre-gyp/-/node-pre-gyp-0.15.0.tgz", + "integrity": "sha512-7QcZa8/fpaU/BKenjcaeFF9hLz2+7S9AqyXFhlH/rilsQ/hPZKK32RtR5EQHJElgu+q5RfbJ34KriI79UWaorA==", + "requires": { + "detect-libc": "^1.0.2", + "mkdirp": "^0.5.3", + "needle": "^2.5.0", + "nopt": "^4.0.1", + "npm-packlist": "^1.1.6", + "npmlog": "^4.0.2", + "rc": "^1.2.7", + "rimraf": "^2.6.1", + "semver": "^5.3.0", + "tar": "^4.4.2" + }, + "dependencies": { + "semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==" + } + } + }, + "nopt": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/nopt/-/nopt-4.0.3.tgz", + "integrity": "sha512-CvaGwVMztSMJLOeXPrez7fyfObdZqNUK1cPAEzLHrTybIua9pMdmmPR5YwtfNftIOMv3DPUhFaxsZMNTQO20Kg==", + "requires": { + "abbrev": "1", + "osenv": "^0.1.4" + } + }, + "npm-bundled": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/npm-bundled/-/npm-bundled-1.1.1.tgz", + "integrity": "sha512-gqkfgGePhTpAEgUsGEgcq1rqPXA+tv/aVBlgEzfXwA1yiUJF7xtEt3CtVwOjNYQOVknDk0F20w58Fnm3EtG0fA==", + "requires": { + "npm-normalize-package-bin": "^1.0.1" + } + }, + "npm-normalize-package-bin": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-1.0.1.tgz", + "integrity": "sha512-EPfafl6JL5/rU+ot6P3gRSCpPDW5VmIzX959Ob1+ySFUuuYHWHekXpwdUZcKP5C+DS4GEtdJluwBjnsNDl+fSA==" + }, + "npm-packlist": { + "version": "1.4.8", + "resolved": "https://registry.npmjs.org/npm-packlist/-/npm-packlist-1.4.8.tgz", + "integrity": "sha512-5+AZgwru5IevF5ZdnFglB5wNlHG1AOOuw28WhUq8/8emhBmLv6jX5by4WJCh7lW0uSYZYS6DXqIsyZVIXRZU9A==", + "requires": { + "ignore-walk": "^3.0.1", + "npm-bundled": "^1.0.1", + "npm-normalize-package-bin": "^1.0.1" + } + }, + "npmlog": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-4.1.2.tgz", + "integrity": "sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg==", + "requires": { + "are-we-there-yet": "~1.1.2", + "console-control-strings": "~1.1.0", + "gauge": "~2.7.3", + "set-blocking": "~2.0.0" + } + }, + "number-is-nan": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", + "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=" + }, + "object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=" + }, "on-finished": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.3.0.tgz", @@ -286,6 +725,33 @@ "ee-first": "1.1.1" } }, + "once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "requires": { + "wrappy": "1" + } + }, + "os-homedir": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", + "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=" + }, + "os-tmpdir": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", + "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=" + }, + "osenv": { + "version": "0.1.5", + "resolved": "https://registry.npmjs.org/osenv/-/osenv-0.1.5.tgz", + "integrity": "sha512-0CWcCECdMVc2Rw3U5w9ZjqX6ga6ubk1xDVKxtBQPK7wis/0F2r9T6k4ydGYhecl7YUBxBVxhL5oisPsNxAPe2g==", + "requires": { + "os-homedir": "^1.0.0", + "os-tmpdir": "^1.0.0" + } + }, "packet-reader": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/packet-reader/-/packet-reader-1.0.0.tgz", @@ -296,6 +762,11 @@ "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==" }, + "path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" + }, "path-to-regexp": { "version": "0.1.7", "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", @@ -378,6 +849,11 @@ "xtend": "^4.0.0" } }, + "process-nextick-args": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", + "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==" + }, "proxy-addr": { "version": "2.0.6", "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.6.tgz", @@ -408,6 +884,17 @@ "unpipe": "1.0.0" } }, + "rc": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", + "requires": { + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" + } + }, "readable-stream": { "version": "3.6.0", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", @@ -426,6 +913,14 @@ "any-promise": "^1.3.0" } }, + "rimraf": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.7.1.tgz", + "integrity": "sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w==", + "requires": { + "glob": "^7.1.3" + } + }, "safe-buffer": { "version": "5.1.2", "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", @@ -436,6 +931,11 @@ "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" }, + "sax": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/sax/-/sax-1.2.4.tgz", + "integrity": "sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw==" + }, "semver": { "version": "7.3.2", "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.2.tgz", @@ -519,11 +1019,21 @@ "send": "0.17.1" } }, + "set-blocking": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", + "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=" + }, "setprototypeof": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.1.tgz", "integrity": "sha512-JvdAWfbXeIGaZ9cILp38HntZSFSo3mWg6xGcJJsd+d4aRMOqauag1C63dJfDw7OaMYwEbHMOxEZ1lqVRYP2OAw==" }, + "signal-exit": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.3.tgz", + "integrity": "sha512-VUJ49FC8U1OxwZLxIbTTrDvLnf/6TDgxZcK8wxR8zs13xpx7xbG60ndBlhNrFi2EMuFRoeDoJO7wthSLq42EjA==" + }, "split2": { "version": "3.2.2", "resolved": "https://registry.npmjs.org/split2/-/split2-3.2.2.tgz", @@ -537,6 +1047,16 @@ "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", "integrity": "sha1-Fhx9rBd2Wf2YEfQ3cfqZOBR4Yow=" }, + "string-width": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", + "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", + "requires": { + "code-point-at": "^1.0.0", + "is-fullwidth-code-point": "^1.0.0", + "strip-ansi": "^3.0.0" + } + }, "string_decoder": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", @@ -552,6 +1072,33 @@ } } }, + "strip-ansi": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", + "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", + "requires": { + "ansi-regex": "^2.0.0" + } + }, + "strip-json-comments": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", + "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=" + }, + "tar": { + "version": "4.4.13", + "resolved": "https://registry.npmjs.org/tar/-/tar-4.4.13.tgz", + "integrity": "sha512-w2VwSrBoHa5BsSyH+KxEqeQBAllHhccyMFVHtGtdMpF4W7IRWfZjFiQceJPChOeTsSDVUpER2T8FA93pr0L+QA==", + "requires": { + "chownr": "^1.1.1", + "fs-minipass": "^1.2.5", + "minipass": "^2.8.6", + "minizlib": "^1.2.1", + "mkdirp": "^0.5.0", + "safe-buffer": "^5.1.2", + "yallist": "^3.0.3" + } + }, "toidentifier": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.0.tgz", @@ -601,6 +1148,14 @@ "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", "integrity": "sha1-IpnwLG3tMNSllhsLn3RSShj2NPw=" }, + "wide-align": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/wide-align/-/wide-align-1.1.3.tgz", + "integrity": "sha512-QGkOQc8XL6Bt5PwnsExKBPuMKBxnGxWWW3fU55Xt4feHozMUhdUMaBCk290qpm/wG5u/RSKzwdAC4i51YigihA==", + "requires": { + "string-width": "^1.0.2 || 2" + } + }, "wkx": { "version": "0.5.0", "resolved": "https://registry.npmjs.org/wkx/-/wkx-0.5.0.tgz", @@ -609,10 +1164,20 @@ "@types/node": "*" } }, + "wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" + }, "xtend": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==" + }, + "yallist": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.1.1.tgz", + "integrity": "sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==" } } } diff --git a/package.json b/package.json index cf235d7..f720410 100644 --- a/package.json +++ b/package.json @@ -19,8 +19,13 @@ }, "homepage": "https://github.com/torianyap/FancyTodo#readme", "dependencies": { + "bcrypt": "^5.0.0", "express": "^4.17.1", + "jsonwebtoken": "^8.5.1", "pg": "^8.4.1", "sequelize": "^6.3.5" + }, + "devDependencies": { + "dotenv": "^8.2.0" } } diff --git a/server/controllers/todoController.js b/server/controllers/todoController.js index 712aaa1..c8008b5 100644 --- a/server/controllers/todoController.js +++ b/server/controllers/todoController.js @@ -3,18 +3,29 @@ const {ToDo} = require('../models/index') class ToDoController { static async create(req, res) { try { - const {title, description, due_date} = req.body - - const newToDo = await ToDo.create({title, description, due_date}, {returning: true}) - res.status(200).json(newToDo) + const payload = { + title: req.body.title, + description: req.body.description, + due_date: req.body.due_date + } + const newToDo = await ToDo.create(payload, { + returning: true + }) + res.status(201).json(newToDo) } catch (error) { - res.status(500).json(error) + if (error.errors) { + res.status(400).json(error.errors[0].message) + } else { + res.status(500).json(error) + } } } static async read(req, res) { try { - const todos = await ToDo.findAll({order: [['id', 'asc']]}) + const todos = await ToDo.findAll({ + order: [['id', 'asc']] + }) res.status(200).json(todos) } catch (error) { res.status(500).json(error) @@ -28,7 +39,7 @@ class ToDoController { if (todo) { res.status(200).json(todo) } else { - throw new Error(`id ${+req.params.id} is not found`) + res.status(404).json({message: `todo with id ${id} is not found`}) } } catch (error) { res.status(500).json(error) @@ -37,18 +48,29 @@ class ToDoController { static async update(req, res) { try { - const id = +req.params.id - const {title, description, due_date} = req.body - - const updated = await ToDo.update( - {title, description, due_date}, - {where: {id: id}, returning: true} - ) - - res.status(200).json(updated[1][0]) + const payload = { + title: req.body.title, + description: req.body.description, + due_date: req.body.due_date + } + const updated = await ToDo.update(payload, { + where: { + id: +req.params.id + }, + returning: true + }) + if (updated[0] !== 1) { + res.status(404).json({message: `todo with id ${+req.params.id} is not found`}) + } else { + res.status(200).json(updated[1][0]) + } } catch (error) { - res.status(500).json(error) + if (error.errors) { + res.status(400).json(error.errors[0].message) + } else { + res.status(500).json(error) + } } } @@ -60,7 +82,11 @@ class ToDoController { }, returning: true }) - res.status(200).json(finished[1][0]) + if (finished[0] !== 1) { + res.status(404).json({message: `todo with id ${+req.params.id} is not found`}) + } else { + res.status(200).json(finished[1][0]) + } } catch (error) { res.status(500).json(error) } @@ -68,12 +94,16 @@ class ToDoController { static async delete(req, res) { try { - await ToDo.destroy({ + const destroyed = await ToDo.destroy({ where: { id: +req.params.id } }) - res.status(200).json({msg: `todo deleted successfuly`}) + if (destroyed !== 1) { + res.status(404).json({message: `id ${+req.params.id} is not found`}) + } else { + res.status(200).json({msg: `todo deleted successfuly`}) + } } catch (error) { res.status(500).json(error) } diff --git a/server/controllers/userController.js b/server/controllers/userController.js new file mode 100644 index 0000000..3b1f431 --- /dev/null +++ b/server/controllers/userController.js @@ -0,0 +1,55 @@ +const { User } = require('../models/index') +const { compare } = require('../helper/bcrypt') +const { signToken } = require('../helper/jwt') + +class UserController { + static async register(req, res) { + try { + const payload = { + email: req.body.email, + password: req.body.password + } + + const user = await User.create(payload) + res.status(200).json({ + id: user.id, + email: user.email + }) + } catch (error) { + res.status(500).json(error) + } + } + + static async login(req, res) { + try { + const payload = { + email: req.body.email, + password: req.body.password + } + + const user = await User.findOne({ + where: { + email: payload.email + } + }) + + if (!user) { + res.status(401).json({message: 'username or password is incorrect'}) + } else if (!compare(payload.password, user.password)) { + res.status(401).json({message: 'username or password is incorrect'}) + } else { + const payload = { + id: user.id, + email:user.email + } + const token = signToken(payload) + res.status(200).json({accessToken: token}) + } + + } catch (error) { + res.status(500).json(error) + } + } +} + +module.exports = UserController \ No newline at end of file diff --git a/server/helper/bcrypt.js b/server/helper/bcrypt.js new file mode 100644 index 0000000..94eafdc --- /dev/null +++ b/server/helper/bcrypt.js @@ -0,0 +1,16 @@ +const bcrypt = require('bcrypt') + +const hashPassword = password => { + const hashed = bcrypt.hashSync(password, +process.env.SALT) + return hashed +} + +const compare = (password, hashed) => { + const result = bcrypt.compareSync(password, hashed) + return result +} + +module.exports = { + hashPassword, + compare +} \ No newline at end of file diff --git a/server/helper/jwt.js b/server/helper/jwt.js new file mode 100644 index 0000000..421b77f --- /dev/null +++ b/server/helper/jwt.js @@ -0,0 +1,10 @@ +const jwt = require('jsonwebtoken') + +const signToken = payload => { + const token = jwt.sign(payload, process.env.SECRET) + return token +} + +module.exports = { + signToken +} \ No newline at end of file diff --git a/server/migrations/20201026094340-create-user.js b/server/migrations/20201026094340-create-user.js new file mode 100644 index 0000000..8d847a8 --- /dev/null +++ b/server/migrations/20201026094340-create-user.js @@ -0,0 +1,30 @@ +'use strict'; +module.exports = { + up: async (queryInterface, Sequelize) => { + await queryInterface.createTable('Users', { + id: { + allowNull: false, + autoIncrement: true, + primaryKey: true, + type: Sequelize.INTEGER + }, + email: { + type: Sequelize.STRING + }, + password: { + type: Sequelize.STRING + }, + createdAt: { + allowNull: false, + type: Sequelize.DATE + }, + updatedAt: { + allowNull: false, + type: Sequelize.DATE + } + }); + }, + down: async (queryInterface, Sequelize) => { + await queryInterface.dropTable('Users'); + } +}; \ No newline at end of file diff --git a/server/models/user.js b/server/models/user.js new file mode 100644 index 0000000..eeb418b --- /dev/null +++ b/server/models/user.js @@ -0,0 +1,35 @@ +'use strict'; +const {Model} = require('sequelize'); +const { hashPassword } = require('../helper/bcrypt') + +module.exports = (sequelize, DataTypes) => { + class User extends Model { + + static associate(models) { + + } + }; + User.init({ + email: { + type: DataTypes.STRING, + validate: { + isEmail: { + args: true, + msg: 'please insert a valid email' + } + } + }, + password: { + type: DataTypes.STRING + } + }, { + sequelize, + modelName: 'User', + }); + + User.addHook('beforeCreate', (instance, options) => { + instance.password = hashPassword(instance.password) + }) + + return User; +}; \ No newline at end of file diff --git a/server/routes/index.js b/server/routes/index.js index f28c3da..b29a3d2 100644 --- a/server/routes/index.js +++ b/server/routes/index.js @@ -1,6 +1,8 @@ const route = require('express').Router() const todoRoute = require('./todoRoute') +const userRoute = require('./userRoute') route.use('/todos', todoRoute) +route.use('/users', userRoute) module.exports = route \ No newline at end of file diff --git a/server/routes/userRoute.js b/server/routes/userRoute.js new file mode 100644 index 0000000..e55e04a --- /dev/null +++ b/server/routes/userRoute.js @@ -0,0 +1,7 @@ +const route = require('express').Router() +const UserController = require('../controllers/userController') + +route.post('/register', UserController.register) +route.post('/login', UserController.login) + +module.exports = route \ No newline at end of file From 4ebf699159bd522ca3088f24489433b8cbf4b22e Mon Sep 17 00:00:00 2001 From: torianyap Date: Tue, 27 Oct 2020 11:45:08 +0700 Subject: [PATCH 07/22] day2 am --- README.md | 2 +- server/controllers/todoController.js | 11 +++- server/helper/jwt.js | 8 ++- server/middlewares/authentication.js | 31 ++++++++++ server/middlewares/authorization.js | 22 +++++++ ...e-user.js => 2020102605111-create-user.js} | 3 + .../migrations/20201026060655-create-to-do.js | 17 ++++++ server/models/todo.js | 57 +++++++++++++++---- server/models/user.js | 22 ++++++- server/routes/todoRoute.js | 13 +++-- 10 files changed, 163 insertions(+), 23 deletions(-) create mode 100644 server/middlewares/authentication.js create mode 100644 server/middlewares/authorization.js rename server/migrations/{20201026094340-create-user.js => 2020102605111-create-user.js} (89%) diff --git a/README.md b/README.md index f8b0fc1..6cd0d2e 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # FancyTodo **Run** -npm run dev +`npm run dev` **Create Todo** ---- diff --git a/server/controllers/todoController.js b/server/controllers/todoController.js index c8008b5..a294349 100644 --- a/server/controllers/todoController.js +++ b/server/controllers/todoController.js @@ -6,7 +6,8 @@ class ToDoController { const payload = { title: req.body.title, description: req.body.description, - due_date: req.body.due_date + due_date: req.body.due_date, + UserId: req.user.id } const newToDo = await ToDo.create(payload, { returning: true @@ -23,8 +24,12 @@ class ToDoController { static async read(req, res) { try { + const UserId = req.user.id const todos = await ToDo.findAll({ - order: [['id', 'asc']] + order: [['id', 'asc']], + where: { + UserId: UserId + } }) res.status(200).json(todos) } catch (error) { @@ -51,7 +56,7 @@ class ToDoController { const payload = { title: req.body.title, description: req.body.description, - due_date: req.body.due_date + due_date: req.body.due_date, } const updated = await ToDo.update(payload, { where: { diff --git a/server/helper/jwt.js b/server/helper/jwt.js index 421b77f..e9d9253 100644 --- a/server/helper/jwt.js +++ b/server/helper/jwt.js @@ -5,6 +5,12 @@ const signToken = payload => { return token } +const verifyToken = token => { + const decoded = jwt.verify(token, process.env.SECRET) + return decoded +} + module.exports = { - signToken + signToken, + verifyToken } \ No newline at end of file diff --git a/server/middlewares/authentication.js b/server/middlewares/authentication.js new file mode 100644 index 0000000..6c76f48 --- /dev/null +++ b/server/middlewares/authentication.js @@ -0,0 +1,31 @@ +const { verifyToken } = require('../helper/jwt') +const { User } = require('../models') + +const authenticate = async (req, res, next) => { + const {access_token} = req.headers + try { + if (!access_token) { + throw { msg: `Authentication failed`, status: 401 } + } else { + const decoded = verifyToken(access_token) + const user = await User.findOne({ + where: { + email: decoded.email + } + }) + if (!user) { + throw { msg: `Authentication failed`, status: 401 } + } else { + req.user = decoded + next() + } + } + } catch (err) { + const status = err.status || 500 + const msg = err.msg || 'Internal Server Error' + + res.status(status).json(msg) + } +} + +module.exports = authenticate \ No newline at end of file diff --git a/server/middlewares/authorization.js b/server/middlewares/authorization.js new file mode 100644 index 0000000..0f2d734 --- /dev/null +++ b/server/middlewares/authorization.js @@ -0,0 +1,22 @@ +const { ToDo } = require('../models') + +const authorization = async (req, res, next) => { + const id = +req.params.id + try { + const todo = await ToDo.findByPk(id) + if (!todo) { + throw { msg: `Todo is not found`, status: 404 } + } else if (todo.UserId !== req.user.id) { + throw { msg: `Not Authorized`, status: 401 } + } else { + next() + } + } catch (err) { + const status = err.status || 500 + const msg = err.msg || 'Internal Server Error' + + res.status(status).json(msg) + } +} + +module.exports = authorization \ No newline at end of file diff --git a/server/migrations/20201026094340-create-user.js b/server/migrations/2020102605111-create-user.js similarity index 89% rename from server/migrations/20201026094340-create-user.js rename to server/migrations/2020102605111-create-user.js index 8d847a8..ed4285e 100644 --- a/server/migrations/20201026094340-create-user.js +++ b/server/migrations/2020102605111-create-user.js @@ -9,9 +9,12 @@ module.exports = { type: Sequelize.INTEGER }, email: { + allowNull: false, + unique: true, type: Sequelize.STRING }, password: { + allowNull: false, type: Sequelize.STRING }, createdAt: { diff --git a/server/migrations/20201026060655-create-to-do.js b/server/migrations/20201026060655-create-to-do.js index 89086b5..656fcfe 100644 --- a/server/migrations/20201026060655-create-to-do.js +++ b/server/migrations/20201026060655-create-to-do.js @@ -1,4 +1,7 @@ 'use strict'; + +const { sequelize } = require("../models"); + module.exports = { up: async (queryInterface, Sequelize) => { await queryInterface.createTable('ToDos', { @@ -9,17 +12,31 @@ module.exports = { type: Sequelize.INTEGER }, title: { + allowNull: false, type: Sequelize.STRING }, description: { + allowNull: false, type: Sequelize.STRING }, status: { + allowNull: false, type: Sequelize.BOOLEAN }, due_date: { + allowNull: false, type: Sequelize.DATE }, + UserId : { + allowNull: false, + type: Sequelize.INTEGER, + references: { + model: 'Users', + key: 'id' + }, + onDelete: 'cascade', + onUpdate: 'cascade' + }, createdAt: { allowNull: false, type: Sequelize.DATE diff --git a/server/models/todo.js b/server/models/todo.js index 223724d..c38bce5 100644 --- a/server/models/todo.js +++ b/server/models/todo.js @@ -3,23 +3,54 @@ const {Model} = require('sequelize'); module.exports = (sequelize, DataTypes) => { class ToDo extends Model { - /** - * Helper method for defining associations. - * This method is not a part of Sequelize lifecycle. - * The `models/index` file will call this method automatically. - */ + static associate(models) { - // define association here + ToDo.belongsTo(models.User, { + foreignKey: 'UserId', + targetKey: 'id' + }) } }; ToDo.init({ - title: DataTypes.STRING, - description: DataTypes.STRING, - status: DataTypes.BOOLEAN, + title: { + type: DataTypes.STRING, + validate: { + notEmpty: { + args: true, + msg: `title can't be empty` + } + } + }, + description: { + type: DataTypes.STRING, + validate: { + notEmpty: { + args: true, + msg: `description can't be empty` + } + } + }, + status: { + type: DataTypes.BOOLEAN, + validate: { + notEmpty: { + args: true, + msg: `status can't be empty` + } + } + }, due_date: { type: DataTypes.DATE, validate: { - costum(value) { + notEmpty : { + args: true, + msg: `due date can't be empty` + }, + isDate: { + args: true, + msg: `must be in date format` + }, + gtToday(value) { const now = new Date() if (now >= value) { throw new Error('due date should be greater than today') @@ -32,8 +63,10 @@ module.exports = (sequelize, DataTypes) => { modelName: 'ToDo', }); - ToDo.addHook('beforeCreate', (instance, options) => { - instance.status = false + ToDo.addHook('beforeValidate', (instance, options) => { + if (!instance.status) { + instance.status = false + } }) return ToDo; diff --git a/server/models/user.js b/server/models/user.js index eeb418b..3fc966a 100644 --- a/server/models/user.js +++ b/server/models/user.js @@ -6,7 +6,7 @@ module.exports = (sequelize, DataTypes) => { class User extends Model { static associate(models) { - + User.hasMany(models.ToDo) } }; User.init({ @@ -16,11 +16,29 @@ module.exports = (sequelize, DataTypes) => { isEmail: { args: true, msg: 'please insert a valid email' + }, + notEmpty: { + args: true, + msg: `email can't be empty` } } }, password: { - type: DataTypes.STRING + type: DataTypes.STRING, + validate: { + notEmpty: { + args: true, + msg: `password can't be empty` + }, + isAlphanumeric: { + args: true, + msg: `password must be alphanumeric` + }, + len: { + args: [5,20], + msg: `password must be a minimal of 5 and a maximum of 20 characters` + } + } } }, { sequelize, diff --git a/server/routes/todoRoute.js b/server/routes/todoRoute.js index b3332fc..a9af4f3 100644 --- a/server/routes/todoRoute.js +++ b/server/routes/todoRoute.js @@ -1,11 +1,16 @@ const route = require('express').Router() const ToDoController = require('../controllers/todoController') +const authenticate = require('../middlewares/authentication') +const authorization = require('../middlewares/authorization') + +route.use(authenticate) route.post('/', ToDoController.create) route.get('/', ToDoController.read) -route.get('/:id', ToDoController.findOne) -route.put('/:id', ToDoController.update) -route.patch('/:id', ToDoController.finish) -route.delete('/:id', ToDoController.delete) + +route.get('/:id', authorization ,ToDoController.findOne) +route.put('/:id', authorization ,ToDoController.update) +route.patch('/:id', authorization ,ToDoController.finish) +route.delete('/:id', authorization ,ToDoController.delete) module.exports = route \ No newline at end of file From 324bd6612f9277950053dcf61ee8a55ac5cd8f70 Mon Sep 17 00:00:00 2001 From: Torian Ariel Yaphet <70468525+torianyap@users.noreply.github.com> Date: Tue, 27 Oct 2020 13:46:02 +0700 Subject: [PATCH 08/22] Delete .env --- .env | 3 --- 1 file changed, 3 deletions(-) delete mode 100644 .env diff --git a/.env b/.env deleted file mode 100644 index 01b4f08..0000000 --- a/.env +++ /dev/null @@ -1,3 +0,0 @@ -SALT=10 -SECRET=redpanda -PORT=3000 \ No newline at end of file From 7a0e54ff6ab3b047789b63304e5468271d588d09 Mon Sep 17 00:00:00 2001 From: torianyap Date: Tue, 27 Oct 2020 15:53:13 +0700 Subject: [PATCH 09/22] day2 pm --- .env | 3 +- .gitignore | 3 +- app.js | 3 ++ package-lock.json | 13 ++++++ package.json | 1 + server/controllers/calendarController.js | 19 +++++++++ server/controllers/todoController.js | 52 ++++++++++-------------- server/controllers/userController.js | 16 ++++---- server/middlewares/authentication.js | 5 +-- server/middlewares/authorization.js | 5 +-- server/middlewares/error_handler.js | 11 +++++ server/routes/calendarRoute.js | 6 +++ server/routes/index.js | 2 + server/routes/todoRoute.js | 10 +++-- 14 files changed, 97 insertions(+), 52 deletions(-) create mode 100644 server/controllers/calendarController.js create mode 100644 server/middlewares/error_handler.js create mode 100644 server/routes/calendarRoute.js diff --git a/.env b/.env index 01b4f08..034103f 100644 --- a/.env +++ b/.env @@ -1,3 +1,4 @@ SALT=10 SECRET=redpanda -PORT=3000 \ No newline at end of file +PORT=3000 +CALENDERIFIC_TOKEN=7c3425cb824f91645a1e56d7f2c74a6914e85ecc \ No newline at end of file diff --git a/.gitignore b/.gitignore index b512c09..1dcef2d 100644 --- a/.gitignore +++ b/.gitignore @@ -1 +1,2 @@ -node_modules \ No newline at end of file +node_modules +.env \ No newline at end of file diff --git a/app.js b/app.js index eee1226..8113a07 100644 --- a/app.js +++ b/app.js @@ -2,11 +2,14 @@ require('dotenv').config() const express = require('express') const router = require('./server/routes') +const error_handler = require('./server/middlewares/error_handler') + const app = express() const port = process.env.PORT app.use(express.json()) app.use(express.urlencoded({extended: true})) app.use(router) +app.use(error_handler) app.listen(port, () => console.log(`listening at ${port}`)) \ No newline at end of file diff --git a/package-lock.json b/package-lock.json index d9717ff..df598d7 100644 --- a/package-lock.json +++ b/package-lock.json @@ -76,6 +76,14 @@ "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", "integrity": "sha1-ml9pkFGx5wczKPKgCJaLZOopVdI=" }, + "axios": { + "version": "0.21.0", + "resolved": "https://registry.npmjs.org/axios/-/axios-0.21.0.tgz", + "integrity": "sha512-fmkJBknJKoZwem3/IKSSLpkdNXZeBu5Q7GA/aRsr2btgrptmSCxi2oFjZHqGdK9DoTil9PIHlPIZw2EcRJXRvw==", + "requires": { + "follow-redirects": "^1.10.0" + } + }, "balanced-match": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", @@ -302,6 +310,11 @@ "unpipe": "~1.0.0" } }, + "follow-redirects": { + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.13.0.tgz", + "integrity": "sha512-aq6gF1BEKje4a9i9+5jimNFIpq4Q1WiwBToeRK5NvZBd/TRsmW8BsJfOEGkr76TbOyPVD3OVDN910EcUNtRYEA==" + }, "forwarded": { "version": "0.1.2", "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.1.2.tgz", diff --git a/package.json b/package.json index f720410..1da84d2 100644 --- a/package.json +++ b/package.json @@ -19,6 +19,7 @@ }, "homepage": "https://github.com/torianyap/FancyTodo#readme", "dependencies": { + "axios": "^0.21.0", "bcrypt": "^5.0.0", "express": "^4.17.1", "jsonwebtoken": "^8.5.1", diff --git a/server/controllers/calendarController.js b/server/controllers/calendarController.js new file mode 100644 index 0000000..1f1ae47 --- /dev/null +++ b/server/controllers/calendarController.js @@ -0,0 +1,19 @@ +const axios = require('axios') + +class CalendarController { + static showHolidays (req, res, next) { + const year = new Date().getFullYear() + axios({ + url: `https://calendarific.com/api/v2/holidays?&api_key=${process.env.CALENDERIFIC_TOKEN}&country=id&year=${year}`, + method: 'get' + }) + .then(result => { + res.status(200).json(result.data.response.holidays) + }) + .catch(err => { + next(err) + }) + } +} + +module.exports = CalendarController \ No newline at end of file diff --git a/server/controllers/todoController.js b/server/controllers/todoController.js index a294349..7b3ca28 100644 --- a/server/controllers/todoController.js +++ b/server/controllers/todoController.js @@ -1,7 +1,7 @@ const {ToDo} = require('../models/index') class ToDoController { - static async create(req, res) { + static async create(req, res, next) { try { const payload = { title: req.body.title, @@ -13,16 +13,12 @@ class ToDoController { returning: true }) res.status(201).json(newToDo) - } catch (error) { - if (error.errors) { - res.status(400).json(error.errors[0].message) - } else { - res.status(500).json(error) - } + } catch (err) { + next(err) } } - static async read(req, res) { + static async read(req, res, next) { try { const UserId = req.user.id const todos = await ToDo.findAll({ @@ -32,26 +28,26 @@ class ToDoController { } }) res.status(200).json(todos) - } catch (error) { - res.status(500).json(error) + } catch (err) { + next(err) } } - static async findOne(req, res) { + static async findOne(req, res, next) { try { const id = +req.params.id const todo = await ToDo.findByPk(id) if (todo) { res.status(200).json(todo) } else { - res.status(404).json({message: `todo with id ${id} is not found`}) + throw { msg: `todo with id ${id} is not found`, status: 404 } } - } catch (error) { - res.status(500).json(error) + } catch (err) { + next(err) } } - static async update(req, res) { + static async update(req, res, next) { try { const payload = { title: req.body.title, @@ -65,21 +61,17 @@ class ToDoController { returning: true }) if (updated[0] !== 1) { - res.status(404).json({message: `todo with id ${+req.params.id} is not found`}) + throw { msg: `todo with id ${+req.params.id} is not found`, status: 404 } } else { res.status(200).json(updated[1][0]) } - } catch (error) { - if (error.errors) { - res.status(400).json(error.errors[0].message) - } else { - res.status(500).json(error) - } + } catch (err) { + next(err) } } - static async finish(req, res) { + static async finish(req, res, next) { try { const finished = await ToDo.update({status: true}, { where: { @@ -88,16 +80,16 @@ class ToDoController { returning: true }) if (finished[0] !== 1) { - res.status(404).json({message: `todo with id ${+req.params.id} is not found`}) + throw { msg: `todo with id ${+req.params.id} is not found`, status: 404 } } else { res.status(200).json(finished[1][0]) } - } catch (error) { - res.status(500).json(error) + } catch (err) { + next(err) } } - static async delete(req, res) { + static async delete(req, res, next) { try { const destroyed = await ToDo.destroy({ where: { @@ -105,12 +97,12 @@ class ToDoController { } }) if (destroyed !== 1) { - res.status(404).json({message: `id ${+req.params.id} is not found`}) + throw { msg: `todo with id ${+req.params.id} is not found`, status: 404 } } else { res.status(200).json({msg: `todo deleted successfuly`}) } - } catch (error) { - res.status(500).json(error) + } catch (err) { + next(err) } } diff --git a/server/controllers/userController.js b/server/controllers/userController.js index 3b1f431..6fb3f10 100644 --- a/server/controllers/userController.js +++ b/server/controllers/userController.js @@ -3,7 +3,7 @@ const { compare } = require('../helper/bcrypt') const { signToken } = require('../helper/jwt') class UserController { - static async register(req, res) { + static async register(req, res, next) { try { const payload = { email: req.body.email, @@ -15,12 +15,12 @@ class UserController { id: user.id, email: user.email }) - } catch (error) { - res.status(500).json(error) + } catch (err) { + next(err) } } - static async login(req, res) { + static async login(req, res, next) { try { const payload = { email: req.body.email, @@ -34,9 +34,9 @@ class UserController { }) if (!user) { - res.status(401).json({message: 'username or password is incorrect'}) + throw { msg: 'username or password is incorrect', status: 401 } } else if (!compare(payload.password, user.password)) { - res.status(401).json({message: 'username or password is incorrect'}) + throw { msg: 'username or password is incorrect', status: 401 } } else { const payload = { id: user.id, @@ -46,8 +46,8 @@ class UserController { res.status(200).json({accessToken: token}) } - } catch (error) { - res.status(500).json(error) + } catch (err) { + next(err) } } } diff --git a/server/middlewares/authentication.js b/server/middlewares/authentication.js index 6c76f48..2a17710 100644 --- a/server/middlewares/authentication.js +++ b/server/middlewares/authentication.js @@ -21,10 +21,7 @@ const authenticate = async (req, res, next) => { } } } catch (err) { - const status = err.status || 500 - const msg = err.msg || 'Internal Server Error' - - res.status(status).json(msg) + next(err) } } diff --git a/server/middlewares/authorization.js b/server/middlewares/authorization.js index 0f2d734..293810b 100644 --- a/server/middlewares/authorization.js +++ b/server/middlewares/authorization.js @@ -12,10 +12,7 @@ const authorization = async (req, res, next) => { next() } } catch (err) { - const status = err.status || 500 - const msg = err.msg || 'Internal Server Error' - - res.status(status).json(msg) + next(err) } } diff --git a/server/middlewares/error_handler.js b/server/middlewares/error_handler.js new file mode 100644 index 0000000..d55fb63 --- /dev/null +++ b/server/middlewares/error_handler.js @@ -0,0 +1,11 @@ +module.exports = function (err, req, res, next) { + let status = err.status || 500 + let msg = err.msg || 'Internal Server Error' + + if (err.name === 'SequelizeValidationError' || err.name === 'SequelizeUniqueConstraintError'){ + status = 400 + msg = err.errors.map(el => el.message).join(', ') + } + console.log(err) + res.status(status).json({msg}) +} \ No newline at end of file diff --git a/server/routes/calendarRoute.js b/server/routes/calendarRoute.js new file mode 100644 index 0000000..0a1a03a --- /dev/null +++ b/server/routes/calendarRoute.js @@ -0,0 +1,6 @@ +const route = require('express').Router() +const CalendarController = require('../controllers/calendarController') + +route.get('/holidays', CalendarController.showHolidays) + +module.exports = route \ No newline at end of file diff --git a/server/routes/index.js b/server/routes/index.js index b29a3d2..3b414e6 100644 --- a/server/routes/index.js +++ b/server/routes/index.js @@ -1,8 +1,10 @@ const route = require('express').Router() const todoRoute = require('./todoRoute') const userRoute = require('./userRoute') +const calendarRoute = require('./calendarRoute') route.use('/todos', todoRoute) route.use('/users', userRoute) +route.use('/calendars', calendarRoute) module.exports = route \ No newline at end of file diff --git a/server/routes/todoRoute.js b/server/routes/todoRoute.js index a9af4f3..e4cb43e 100644 --- a/server/routes/todoRoute.js +++ b/server/routes/todoRoute.js @@ -8,9 +8,11 @@ route.use(authenticate) route.post('/', ToDoController.create) route.get('/', ToDoController.read) -route.get('/:id', authorization ,ToDoController.findOne) -route.put('/:id', authorization ,ToDoController.update) -route.patch('/:id', authorization ,ToDoController.finish) -route.delete('/:id', authorization ,ToDoController.delete) +route.use('/:id', authorization) + +route.get('/:id', ToDoController.findOne) +route.put('/:id', ToDoController.update) +route.patch('/:id', ToDoController.finish) +route.delete('/:id', ToDoController.delete) module.exports = route \ No newline at end of file From 814597605c73a433d9ac936d33f379c60496c2f2 Mon Sep 17 00:00:00 2001 From: torianyap Date: Tue, 27 Oct 2020 16:15:49 +0700 Subject: [PATCH 10/22] Stopped tracking .env file --- .env | 4 ---- 1 file changed, 4 deletions(-) delete mode 100644 .env diff --git a/.env b/.env deleted file mode 100644 index 034103f..0000000 --- a/.env +++ /dev/null @@ -1,4 +0,0 @@ -SALT=10 -SECRET=redpanda -PORT=3000 -CALENDERIFIC_TOKEN=7c3425cb824f91645a1e56d7f2c74a6914e85ecc \ No newline at end of file From 94af18628a0351c5441680d838c8f13d979830c0 Mon Sep 17 00:00:00 2001 From: torianyap Date: Tue, 27 Oct 2020 18:07:48 +0700 Subject: [PATCH 11/22] revisi --- server/controllers/calendarController.js | 3 ++- server/controllers/weatherController.js | 19 ++++++++++++++++++ server/middlewares/error_handler.js | 4 +++- .../migrations/2020102605111-create-user.js | 4 ---- .../migrations/20201026060655-create-to-do.js | 7 ------- server/models/todo.js | 20 +++++++++++++++++++ server/models/user.js | 10 ++++++++++ server/routes/calendarRoute.js | 2 +- server/routes/index.js | 4 +++- server/routes/weatherRoute.js | 6 ++++++ 10 files changed, 64 insertions(+), 15 deletions(-) create mode 100644 server/controllers/weatherController.js create mode 100644 server/routes/weatherRoute.js diff --git a/server/controllers/calendarController.js b/server/controllers/calendarController.js index 1f1ae47..704b082 100644 --- a/server/controllers/calendarController.js +++ b/server/controllers/calendarController.js @@ -2,9 +2,10 @@ const axios = require('axios') class CalendarController { static showHolidays (req, res, next) { + const country = req.params.country const year = new Date().getFullYear() axios({ - url: `https://calendarific.com/api/v2/holidays?&api_key=${process.env.CALENDERIFIC_TOKEN}&country=id&year=${year}`, + url: `https://calendarific.com/api/v2/holidays?&api_key=${process.env.CALENDERIFIC_TOKEN}&country=${country}&year=${year}`, method: 'get' }) .then(result => { diff --git a/server/controllers/weatherController.js b/server/controllers/weatherController.js new file mode 100644 index 0000000..8f274ec --- /dev/null +++ b/server/controllers/weatherController.js @@ -0,0 +1,19 @@ +const axios = require('axios') + +class WeatherController { + static currentWeather (req, res, next) { + const q = req.params.city // e.g: Jakarta,id / London / Brazil / dll + axios({ + url: `http://api.openweathermap.org/data/2.5/weather?q=${q}&appid=${process.env.WEATHER}`, + method: 'get' + }) + .then(result => { + res.status(200).json(result.data) + }) + .catch(err => { + next(err) + }) + } +} + +module.exports = WeatherController \ No newline at end of file diff --git a/server/middlewares/error_handler.js b/server/middlewares/error_handler.js index d55fb63..120e418 100644 --- a/server/middlewares/error_handler.js +++ b/server/middlewares/error_handler.js @@ -5,7 +5,9 @@ module.exports = function (err, req, res, next) { if (err.name === 'SequelizeValidationError' || err.name === 'SequelizeUniqueConstraintError'){ status = 400 msg = err.errors.map(el => el.message).join(', ') + } else if (err.response.data) { + status = err.response.data.cod + msg = err.response.data.message } - console.log(err) res.status(status).json({msg}) } \ No newline at end of file diff --git a/server/migrations/2020102605111-create-user.js b/server/migrations/2020102605111-create-user.js index ed4285e..1a1f21a 100644 --- a/server/migrations/2020102605111-create-user.js +++ b/server/migrations/2020102605111-create-user.js @@ -9,20 +9,16 @@ module.exports = { type: Sequelize.INTEGER }, email: { - allowNull: false, unique: true, type: Sequelize.STRING }, password: { - allowNull: false, type: Sequelize.STRING }, createdAt: { - allowNull: false, type: Sequelize.DATE }, updatedAt: { - allowNull: false, type: Sequelize.DATE } }); diff --git a/server/migrations/20201026060655-create-to-do.js b/server/migrations/20201026060655-create-to-do.js index 656fcfe..46ab270 100644 --- a/server/migrations/20201026060655-create-to-do.js +++ b/server/migrations/20201026060655-create-to-do.js @@ -12,23 +12,18 @@ module.exports = { type: Sequelize.INTEGER }, title: { - allowNull: false, type: Sequelize.STRING }, description: { - allowNull: false, type: Sequelize.STRING }, status: { - allowNull: false, type: Sequelize.BOOLEAN }, due_date: { - allowNull: false, type: Sequelize.DATE }, UserId : { - allowNull: false, type: Sequelize.INTEGER, references: { model: 'Users', @@ -38,11 +33,9 @@ module.exports = { onUpdate: 'cascade' }, createdAt: { - allowNull: false, type: Sequelize.DATE }, updatedAt: { - allowNull: false, type: Sequelize.DATE } }); diff --git a/server/models/todo.js b/server/models/todo.js index c38bce5..40c1d9c 100644 --- a/server/models/todo.js +++ b/server/models/todo.js @@ -14,7 +14,12 @@ module.exports = (sequelize, DataTypes) => { ToDo.init({ title: { type: DataTypes.STRING, + allowNull: false, validate: { + notNull: { + args: true, + msg: `title can't be empty` + }, notEmpty: { args: true, msg: `title can't be empty` @@ -23,29 +28,44 @@ module.exports = (sequelize, DataTypes) => { }, description: { type: DataTypes.STRING, + allowNull: false, validate: { notEmpty: { args: true, msg: `description can't be empty` + }, + notNull: { + args: true, + msg: `description can't be empty` } } }, status: { type: DataTypes.BOOLEAN, + allowNull: false, validate: { notEmpty: { args: true, msg: `status can't be empty` + }, + notNull: { + args: true, + msg: `status can't be empty` } } }, due_date: { type: DataTypes.DATE, + allowNull: false, validate: { notEmpty : { args: true, msg: `due date can't be empty` }, + notNull: { + args: true, + msg: `due date can't be empty` + }, isDate: { args: true, msg: `must be in date format` diff --git a/server/models/user.js b/server/models/user.js index 3fc966a..f04fe35 100644 --- a/server/models/user.js +++ b/server/models/user.js @@ -12,6 +12,7 @@ module.exports = (sequelize, DataTypes) => { User.init({ email: { type: DataTypes.STRING, + allowNull: false, validate: { isEmail: { args: true, @@ -20,12 +21,21 @@ module.exports = (sequelize, DataTypes) => { notEmpty: { args: true, msg: `email can't be empty` + }, + notNull: { + args: true, + msg: `email can't be empty` } } }, password: { type: DataTypes.STRING, + allowNull: false, validate: { + notNull: { + args: true, + msg: `password can't be empty` + }, notEmpty: { args: true, msg: `password can't be empty` diff --git a/server/routes/calendarRoute.js b/server/routes/calendarRoute.js index 0a1a03a..7923c97 100644 --- a/server/routes/calendarRoute.js +++ b/server/routes/calendarRoute.js @@ -1,6 +1,6 @@ const route = require('express').Router() const CalendarController = require('../controllers/calendarController') -route.get('/holidays', CalendarController.showHolidays) +route.get('/:country', CalendarController.showHolidays) module.exports = route \ No newline at end of file diff --git a/server/routes/index.js b/server/routes/index.js index 3b414e6..f647261 100644 --- a/server/routes/index.js +++ b/server/routes/index.js @@ -2,9 +2,11 @@ const route = require('express').Router() const todoRoute = require('./todoRoute') const userRoute = require('./userRoute') const calendarRoute = require('./calendarRoute') +const weatherRoute = require('./weatherRoute') route.use('/todos', todoRoute) route.use('/users', userRoute) -route.use('/calendars', calendarRoute) +route.use('/holidays', calendarRoute) +route.use('/weathers', weatherRoute) module.exports = route \ No newline at end of file diff --git a/server/routes/weatherRoute.js b/server/routes/weatherRoute.js new file mode 100644 index 0000000..ceca306 --- /dev/null +++ b/server/routes/weatherRoute.js @@ -0,0 +1,6 @@ +const route = require('express').Router() +const WeatherController = require('../controllers/weatherController') + +route.get('/:city', WeatherController.currentWeather) + +module.exports = route \ No newline at end of file From cd60d556ec4e8a1da74cd4b30d60834cb04af506 Mon Sep 17 00:00:00 2001 From: torianyap Date: Wed, 28 Oct 2020 19:15:36 +0700 Subject: [PATCH 12/22] day3 pm --- client/index.html | 119 ++++- client/index.js | 276 +++++++++++ .gitignore => server/.gitignore | 0 app.js => server/app.js | 6 +- server/controllers/calendarController.js | 20 - server/controllers/userController.js | 42 ++ server/middlewares/error_handler.js | 4 +- package-lock.json => server/package-lock.json | 461 ++++++++++++++---- package.json => server/package.json | 16 +- server/routes/calendarRoute.js | 6 - server/routes/index.js | 2 - server/routes/userRoute.js | 1 + 12 files changed, 805 insertions(+), 148 deletions(-) create mode 100644 client/index.js rename .gitignore => server/.gitignore (100%) rename app.js => server/app.js (66%) delete mode 100644 server/controllers/calendarController.js rename package-lock.json => server/package-lock.json (75%) rename package.json => server/package.json (57%) delete mode 100644 server/routes/calendarRoute.js diff --git a/client/index.html b/client/index.html index 69763a7..aed4152 100644 --- a/client/index.html +++ b/client/index.html @@ -3,9 +3,124 @@ - Document + + + + + Fancy ToDo - + + + + +
+ +
+

Register


+ +
+
+ + +
+
+ + +
+ +
+
+ + + +
+

Login


+ +
+
+ + +
+
+ + +
+

+
+

+
+ + + +
+

Here Are Your ToDo list

+ +

+ + +
+ +
+ + + + + + + + + +
+ + +
+ + + \ No newline at end of file diff --git a/client/index.js b/client/index.js new file mode 100644 index 0000000..aa1d34a --- /dev/null +++ b/client/index.js @@ -0,0 +1,276 @@ +const SERVER = 'http://localhost:3000' + +function beforeLogin() { + $('#register').hide() + $('#login').show() + $('#content').hide() + $('todos').hide() + $('#form-addToDo').hide() + $('form-updateTodo').hide() +} + +function afterLogin() { + $('#register').hide() + $('#login').hide() + $('#content').show() + $('#form-addToDo').hide() + $('#form-updateTodo').hide() + fetchToDos() +} + +$(document).ready( _ => { + const token = localStorage.getItem('access_token') + if (token) { + afterLogin() + } else { + beforeLogin() + } +}) + +//move to login +$('#nav-login').on('click', () => { + $('#register').hide() + $('#login').show() + $('#content').hide() +}) + +//move to register +$('#nav-register').on('click', () => { + $('#register').show() + $('#login').hide() + $('#content').hide() +}) + +//register +const register = e => { + e.preventDefault() + const email = $('#register-email').val() + const password = $('#register-pwd').val() + + $.ajax({ + method: 'POST', + url: `${SERVER}/users/register`, + data: { + email, + password + } + }) + .done(response => { + $('#register').hide() + $('#login').show() + $('#todo').hide() + }) + .fail(err => { + console.log(err) + }) +} + +//login +const login = e => { + e.preventDefault() + + const email = $('#login-email').val() + const password = $('#login-pwd').val() + + $.ajax({ + method: 'POST', + url: `${SERVER}/users/login`, + data: { + email, + password + } + }) + .done(response => { + $('#register').hide() + $('#login').hide() + $('#todo').show() + const access_token = response.accessToken + + localStorage.setItem('access_token', access_token) + fetchToDos() + }) + .fail(err => { + console.log(err) + }) +} + +function onSignIn(googleUser) { + const google_access_token = googleUser.getAuthResponse().id_token; + $.ajax({ + method:'POST', + url: `${SERVER}/users/googleLogin`, + data: { + google_access_token + } + }) + .done(response => { + localStorage.setItem('access_token', response.access_token) + afterLogin() + }) + .fail(err => { + console.log(err) + }) +} + +//logout +$('#nav-logout').on('click', () => { + beforeLogin() + + localStorage.removeItem('access_token') + signOut() +}) + +function signOut() { + const auth2 = gapi.auth2.getAuthInstance(); + auth2.signOut().then(function () { + console.log('User signed out.'); + } +)}; + +//readAll +const fetchToDos = () => { + const access_token = localStorage.getItem('access_token') + $('#todos').empty() + $.ajax({ + method: 'GET', + url: `${SERVER}/todos`, + headers : { + access_token: access_token + } + }) + .done(response => { + console.log(response) + if (response[0]) { + response.forEach(el => { + if(el.status === false) { + $('#todos').append(` +

${el.title.toUpperCase()}

+

${el.description}

+

${new Date(el.due_date)}

+ + + +
+ `) + } else { + $('#todos').append(` +

${el.title.toUpperCase()}

+

${el.description}

+

${new Date(el.due_date)}

+ Finish + +
+ `) + } + }) + } else { + $('#todos').append(`
There's nothing here
Start adding some task
`) + } + }) + .fail(err => { + console.log(err) + }) +} + +//addTodo +const addTodo = () => { + const access_token = localStorage.getItem('access_token') + const title = $('#title').val() + const description = $('#description').val() + const due_date = $('#due_date').val() + + $.ajax({ + method: 'POST', + url: `${SERVER}/todos`, + data: { + title, + description, + due_date + }, + headers: { + access_token + } + }) + .done(response => { + afterLogin() + + }) + .fail(err => { + console.log(err) + }) +} + +$('#addTodo').on('click', () => { + $('#form-addToDo').show() +}) + +//updateTodo +let goingToBeUpdated; + +const updateToDo = id => { + id = goingToBeUpdated + const access_token = localStorage.getItem('access_token') + const title = $('#update_title').val() + const description = $('#update_description').val() + const due_date = $('#update_due_date').val() + + $.ajax({ + method: 'PUT', + url: `${SERVER}/todos/${id}`, + headers: { + access_token: access_token + }, + data: { + title, + description, + due_date + } + }) + .done(response => { + afterLogin() + }) + .fail(err => { + console.log(err) + }) +} + +const updateToDoForm = (id) => { + $('#form-updateTodo').show() + goingToBeUpdated = id +} + +//finishTodo +const finishToDo = id => { + const access_token = localStorage.getItem('access_token') + $.ajax({ + method: 'PATCH', + url: `${SERVER}/todos/${id}`, + headers: { + access_token: access_token + } + }) + .done(response => { + afterLogin() + }) + .fail(err => { + console.log(err) + }) +} + +//deleteToDo +const deleteToDo = id => { + const access_token = localStorage.getItem('access_token') + $.ajax({ + method: 'DELETE', + url: `${SERVER}/todos/${id}`, + headers: { + access_token: access_token + } + }) + .done(response => { + afterLogin() + }) + .fail(err => { + console.log(err) + }) +} \ No newline at end of file diff --git a/.gitignore b/server/.gitignore similarity index 100% rename from .gitignore rename to server/.gitignore diff --git a/app.js b/server/app.js similarity index 66% rename from app.js rename to server/app.js index 8113a07..8629e38 100644 --- a/app.js +++ b/server/app.js @@ -1,12 +1,14 @@ require('dotenv').config() const express = require('express') -const router = require('./server/routes') -const error_handler = require('./server/middlewares/error_handler') +const cors = require('cors') +const router = require('./routes') +const error_handler = require('./middlewares/error_handler') const app = express() const port = process.env.PORT +app.use(cors()) app.use(express.json()) app.use(express.urlencoded({extended: true})) app.use(router) diff --git a/server/controllers/calendarController.js b/server/controllers/calendarController.js deleted file mode 100644 index 704b082..0000000 --- a/server/controllers/calendarController.js +++ /dev/null @@ -1,20 +0,0 @@ -const axios = require('axios') - -class CalendarController { - static showHolidays (req, res, next) { - const country = req.params.country - const year = new Date().getFullYear() - axios({ - url: `https://calendarific.com/api/v2/holidays?&api_key=${process.env.CALENDERIFIC_TOKEN}&country=${country}&year=${year}`, - method: 'get' - }) - .then(result => { - res.status(200).json(result.data.response.holidays) - }) - .catch(err => { - next(err) - }) - } -} - -module.exports = CalendarController \ No newline at end of file diff --git a/server/controllers/userController.js b/server/controllers/userController.js index 6fb3f10..90651da 100644 --- a/server/controllers/userController.js +++ b/server/controllers/userController.js @@ -1,6 +1,7 @@ const { User } = require('../models/index') const { compare } = require('../helper/bcrypt') const { signToken } = require('../helper/jwt') +const {OAuth2Client} = require('google-auth-library'); class UserController { static async register(req, res, next) { @@ -50,6 +51,47 @@ class UserController { next(err) } } + + static googleLogin (req, res, next) { + const {google_access_token} = req.body + const client = new OAuth2Client(process.env.CLIENT_ID); + + let email + client.verifyIdToken({ + idToken: google_access_token, + audience: process.env.CLIENT_ID + }) + .then(ticket => { + const payload = ticket.getPayload() + email = payload.email + return User.findOne({ + where: { + email: payload.email + } + }) + }) + .then(user => { + if (user) { + return user + }else { + const obj = { + email: email, + password: 'incorrect329' + } + return User.create(obj) + } + }) + .then(data => { + const access_token = signToken({ + id: data.id, + email: data.email + }) + return res.status(200).json({access_token}) + }) + .catch(err => { + next(err) + }) + } } module.exports = UserController \ No newline at end of file diff --git a/server/middlewares/error_handler.js b/server/middlewares/error_handler.js index 120e418..d55fb63 100644 --- a/server/middlewares/error_handler.js +++ b/server/middlewares/error_handler.js @@ -5,9 +5,7 @@ module.exports = function (err, req, res, next) { if (err.name === 'SequelizeValidationError' || err.name === 'SequelizeUniqueConstraintError'){ status = 400 msg = err.errors.map(el => el.message).join(', ') - } else if (err.response.data) { - status = err.response.data.cod - msg = err.response.data.message } + console.log(err) res.status(status).json({msg}) } \ No newline at end of file diff --git a/package-lock.json b/server/package-lock.json similarity index 75% rename from package-lock.json rename to server/package-lock.json index df598d7..894f1fd 100644 --- a/package-lock.json +++ b/server/package-lock.json @@ -5,15 +5,23 @@ "requires": true, "dependencies": { "@types/node": { - "version": "14.14.3", - "resolved": "https://registry.npmjs.org/@types/node/-/node-14.14.3.tgz", - "integrity": "sha512-33/L34xS7HVUx23e0wOT2V1qPF1IrHgQccdJVm9uXGTB9vFBrrzBtkQymT8VskeKOxjz55MSqMv0xuLq+u98WQ==" + "version": "14.14.5", + "resolved": "https://registry.npmjs.org/@types/node/-/node-14.14.5.tgz", + "integrity": "sha512-H5Wn24s/ZOukBmDn03nnGTp18A60ny9AmCwnEcgJiTgSGsCO7k+NWP7zjCCbhlcnVCoI+co52dUAt9GMhOSULw==" }, "abbrev": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz", "integrity": "sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==" }, + "abort-controller": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/abort-controller/-/abort-controller-3.0.0.tgz", + "integrity": "sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==", + "requires": { + "event-target-shim": "^5.0.0" + } + }, "accepts": { "version": "1.3.7", "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.7.tgz", @@ -23,6 +31,24 @@ "negotiator": "0.6.2" } }, + "agent-base": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-6.0.2.tgz", + "integrity": "sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==", + "requires": { + "debug": "4" + }, + "dependencies": { + "debug": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.2.0.tgz", + "integrity": "sha512-IX2ncY78vDTjZMFUdmsvIRFY2Cf4FnD0wRs+nQwJU8Lu99/tPFdb0VybiiMTPe3I6rQmwsqQqRBvxU+bZ/I8sg==", + "requires": { + "ms": "2.1.2" + } + } + } + }, "ansi-regex": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", @@ -45,30 +71,6 @@ "requires": { "delegates": "^1.0.0", "readable-stream": "^2.0.6" - }, - "dependencies": { - "readable-stream": { - "version": "2.3.7", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.7.tgz", - "integrity": "sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==", - "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" - } - }, - "string_decoder": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", - "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", - "requires": { - "safe-buffer": "~5.1.0" - } - } } }, "array-flatten": { @@ -76,6 +78,11 @@ "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", "integrity": "sha1-ml9pkFGx5wczKPKgCJaLZOopVdI=" }, + "arrify": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/arrify/-/arrify-2.0.1.tgz", + "integrity": "sha512-3duEwti880xqi4eAMN8AyR4a0ByT90zoYdLlevfrvU43vb0YZwZVfxOgxWrLXXXpyugL0hNZc9G6BiB5B3nUug==" + }, "axios": { "version": "0.21.0", "resolved": "https://registry.npmjs.org/axios/-/axios-0.21.0.tgz", @@ -89,6 +96,11 @@ "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" }, + "base64-js": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.3.1.tgz", + "integrity": "sha512-mLQ4i2QO1ytvGWFWmcngKO//JXAQueZvwEKtjgQFM4jIK0kU+ytMfplL8j+n5mspOfjHwoAg+9yhb7BwAHm36g==" + }, "bcrypt": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/bcrypt/-/bcrypt-5.0.0.tgz", @@ -98,6 +110,11 @@ "node-pre-gyp": "0.15.0" } }, + "bignumber.js": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/bignumber.js/-/bignumber.js-9.0.1.tgz", + "integrity": "sha512-IdZR9mh6ahOBv/hYGiXyVuyCetmGJhtYkqLBpTStdhEGjegpPlUawydyaF3pbIOFynJTpllEs+NP+CS9jKFLjA==" + }, "body-parser": { "version": "1.19.0", "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.19.0.tgz", @@ -113,6 +130,21 @@ "qs": "6.7.0", "raw-body": "2.4.0", "type-is": "~1.6.17" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "requires": { + "ms": "2.0.0" + } + }, + "ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" + } } }, "brace-expansion": { @@ -187,12 +219,21 @@ "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" }, + "cors": { + "version": "2.8.5", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", + "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", + "requires": { + "object-assign": "^4", + "vary": "^1" + } + }, "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "version": "3.2.6", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz", + "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==", "requires": { - "ms": "2.0.0" + "ms": "^2.1.1" } }, "deep-extend": { @@ -259,6 +300,11 @@ "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", "integrity": "sha1-Qa4u62XvpiJorr/qg6x9eSmbCIc=" }, + "event-target-shim": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-5.0.1.tgz", + "integrity": "sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==" + }, "express": { "version": "4.17.1", "resolved": "https://registry.npmjs.org/express/-/express-4.17.1.tgz", @@ -294,8 +340,33 @@ "type-is": "~1.6.18", "utils-merge": "1.0.1", "vary": "~1.1.2" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "requires": { + "ms": "2.0.0" + } + }, + "ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" + } } }, + "extend": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==" + }, + "fast-text-encoding": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/fast-text-encoding/-/fast-text-encoding-1.0.3.tgz", + "integrity": "sha512-dtm4QZH9nZtcDt8qJiOH9fcQd1NAgi+K1O2DbE6GG1PPCK/BWfOH3idCTRQ4ImXRUOyopDEgDEnVEE7Y/2Wrig==" + }, "finalhandler": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.2.tgz", @@ -308,6 +379,21 @@ "parseurl": "~1.3.3", "statuses": "~1.5.0", "unpipe": "~1.0.0" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "requires": { + "ms": "2.0.0" + } + }, + "ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" + } } }, "follow-redirects": { @@ -353,6 +439,41 @@ "wide-align": "^1.1.0" } }, + "gaxios": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-4.0.1.tgz", + "integrity": "sha512-jOin8xRZ/UytQeBpSXFqIzqU7Fi5TqgPNLlUsSB8kjJ76+FiGBfImF8KJu++c6J4jOldfJUtt0YmkRj2ZpSHTQ==", + "requires": { + "abort-controller": "^3.0.0", + "extend": "^3.0.2", + "https-proxy-agent": "^5.0.0", + "is-stream": "^2.0.0", + "node-fetch": "^2.3.0" + } + }, + "gcp-metadata": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/gcp-metadata/-/gcp-metadata-4.2.0.tgz", + "integrity": "sha512-vQZD57cQkqIA6YPGXM/zc+PIZfNRFdukWGsGZ5+LcJzesi5xp6Gn7a02wRJi4eXPyArNMIYpPET4QMxGqtlk6Q==", + "requires": { + "gaxios": "^3.0.0", + "json-bigint": "^1.0.0" + }, + "dependencies": { + "gaxios": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-3.2.0.tgz", + "integrity": "sha512-+6WPeVzPvOshftpxJwRi2Ozez80tn/hdtOUag7+gajDHRJvAblKxTFSSMPtr2hmnLy7p0mvYz0rMXLBl8pSO7Q==", + "requires": { + "abort-controller": "^3.0.0", + "extend": "^3.0.2", + "https-proxy-agent": "^5.0.0", + "is-stream": "^2.0.0", + "node-fetch": "^2.3.0" + } + } + } + }, "glob": { "version": "7.1.6", "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.6.tgz", @@ -366,6 +487,88 @@ "path-is-absolute": "^1.0.0" } }, + "google-auth-library": { + "version": "6.1.3", + "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-6.1.3.tgz", + "integrity": "sha512-m9mwvY3GWbr7ZYEbl61isWmk+fvTmOt0YNUfPOUY2VH8K5pZlAIWJjxEi0PqR3OjMretyiQLI6GURMrPSwHQ2g==", + "requires": { + "arrify": "^2.0.0", + "base64-js": "^1.3.0", + "ecdsa-sig-formatter": "^1.0.11", + "fast-text-encoding": "^1.0.0", + "gaxios": "^4.0.0", + "gcp-metadata": "^4.2.0", + "gtoken": "^5.0.4", + "jws": "^4.0.0", + "lru-cache": "^6.0.0" + }, + "dependencies": { + "jwa": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/jwa/-/jwa-2.0.0.tgz", + "integrity": "sha512-jrZ2Qx916EA+fq9cEAeCROWPTfCwi1IVHqT2tapuqLEVVDKFDENFw1oL+MwrTvH6msKxsd1YTDVw6uKEcsrLEA==", + "requires": { + "buffer-equal-constant-time": "1.0.1", + "ecdsa-sig-formatter": "1.0.11", + "safe-buffer": "^5.0.1" + } + }, + "jws": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/jws/-/jws-4.0.0.tgz", + "integrity": "sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==", + "requires": { + "jwa": "^2.0.0", + "safe-buffer": "^5.0.1" + } + } + } + }, + "google-p12-pem": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/google-p12-pem/-/google-p12-pem-3.0.3.tgz", + "integrity": "sha512-wS0ek4ZtFx/ACKYF3JhyGe5kzH7pgiQ7J5otlumqR9psmWMYc+U9cErKlCYVYHoUaidXHdZ2xbo34kB+S+24hA==", + "requires": { + "node-forge": "^0.10.0" + } + }, + "gtoken": { + "version": "5.0.5", + "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-5.0.5.tgz", + "integrity": "sha512-wvjkecutFh8kVfbcdBdUWqDRrXb+WrgD79DBDEYf1Om8S1FluhylhtFjrL7Tx69vNhh259qA3Q1P4sPtb+kUYw==", + "requires": { + "gaxios": "^4.0.0", + "google-p12-pem": "^3.0.3", + "jws": "^4.0.0", + "mime": "^2.2.0" + }, + "dependencies": { + "jwa": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/jwa/-/jwa-2.0.0.tgz", + "integrity": "sha512-jrZ2Qx916EA+fq9cEAeCROWPTfCwi1IVHqT2tapuqLEVVDKFDENFw1oL+MwrTvH6msKxsd1YTDVw6uKEcsrLEA==", + "requires": { + "buffer-equal-constant-time": "1.0.1", + "ecdsa-sig-formatter": "1.0.11", + "safe-buffer": "^5.0.1" + } + }, + "jws": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/jws/-/jws-4.0.0.tgz", + "integrity": "sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==", + "requires": { + "jwa": "^2.0.0", + "safe-buffer": "^5.0.1" + } + }, + "mime": { + "version": "2.4.6", + "resolved": "https://registry.npmjs.org/mime/-/mime-2.4.6.tgz", + "integrity": "sha512-RZKhC3EmpBchfTGBVb8fb+RL2cWyw/32lshnsETttkBAyAUXSGHxbEJWWRXc751DrIxG1q04b8QwMbAwkRPpUA==" + } + } + }, "has-unicode": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz", @@ -381,6 +584,32 @@ "setprototypeof": "1.1.1", "statuses": ">= 1.5.0 < 2", "toidentifier": "1.0.0" + }, + "dependencies": { + "inherits": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", + "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" + } + } + }, + "https-proxy-agent": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-5.0.0.tgz", + "integrity": "sha512-EkYm5BcKUGiduxzSt3Eppko+PiNWNEpa4ySk9vTC6wDsQJW9rHSa+UhGNJoRYp7bz6Ht1eaRIa6QaJqO5rCFbA==", + "requires": { + "agent-base": "6", + "debug": "4" + }, + "dependencies": { + "debug": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.2.0.tgz", + "integrity": "sha512-IX2ncY78vDTjZMFUdmsvIRFY2Cf4FnD0wRs+nQwJU8Lu99/tPFdb0VybiiMTPe3I6rQmwsqQqRBvxU+bZ/I8sg==", + "requires": { + "ms": "2.1.2" + } + } } }, "iconv-lite": { @@ -414,9 +643,9 @@ } }, "inherits": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==" }, "ini": { "version": "1.3.5", @@ -436,11 +665,24 @@ "number-is-nan": "^1.0.0" } }, + "is-stream": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.0.tgz", + "integrity": "sha512-XCoy+WlUr7d1+Z8GgSuXmpuUFC9fOhRXglJMx+dwLKTkL44Cjd4W1Z5P+BQZpr+cR93aGP4S/s7Ftw6Nd/kiEw==" + }, "isarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" }, + "json-bigint": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/json-bigint/-/json-bigint-1.0.0.tgz", + "integrity": "sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ==", + "requires": { + "bignumber.js": "^9.0.0" + } + }, "jsonwebtoken": { "version": "8.5.1", "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-8.5.1.tgz", @@ -456,18 +698,6 @@ "lodash.once": "^4.0.0", "ms": "^2.1.1", "semver": "^5.6.0" - }, - "dependencies": { - "ms": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" - }, - "semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==" - } } }, "jwa": { @@ -529,6 +759,21 @@ "resolved": "https://registry.npmjs.org/lodash.once/-/lodash.once-4.1.1.tgz", "integrity": "sha1-DdOXEhPHxW34gJd9UEyI+0cal6w=" }, + "lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "requires": { + "yallist": "^4.0.0" + }, + "dependencies": { + "yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==" + } + } + }, "media-typer": { "version": "0.3.0", "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", @@ -614,9 +859,9 @@ } }, "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" }, "needle": { "version": "2.5.2", @@ -626,21 +871,6 @@ "debug": "^3.2.6", "iconv-lite": "^0.4.4", "sax": "^1.2.4" - }, - "dependencies": { - "debug": { - "version": "3.2.6", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz", - "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==", - "requires": { - "ms": "^2.1.1" - } - }, - "ms": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" - } } }, "negotiator": { @@ -653,6 +883,16 @@ "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-3.0.2.tgz", "integrity": "sha512-+D4s2HCnxPd5PjjI0STKwncjXTUKKqm74MDMz9OPXavjsGmjkvwgLtA5yoxJUdmpj52+2u+RrXgPipahKczMKg==" }, + "node-fetch": { + "version": "2.6.1", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.1.tgz", + "integrity": "sha512-V4aYg89jEoVRxRb2fJdAg8FHvI7cEyYdVAh94HH0UIK8oJxUfkjlDQN9RbMx+bEjP7+ggMiFRprSti032Oipxw==" + }, + "node-forge": { + "version": "0.10.0", + "resolved": "https://registry.npmjs.org/node-forge/-/node-forge-0.10.0.tgz", + "integrity": "sha512-PPmu8eEeG9saEUvI97fm4OYxXVB6bFvyNTyiUOBichBpFG8A1Ljw3bY62+5oOjDEMHRnd0Y7HQ+x7uzxOzC6JA==" + }, "node-pre-gyp": { "version": "0.15.0", "resolved": "https://registry.npmjs.org/node-pre-gyp/-/node-pre-gyp-0.15.0.tgz", @@ -668,13 +908,6 @@ "rimraf": "^2.6.1", "semver": "^5.3.0", "tar": "^4.4.2" - }, - "dependencies": { - "semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==" - } } }, "nopt": { @@ -786,14 +1019,14 @@ "integrity": "sha1-32BBeABfUi8V60SQ5yR6G/qmf4w=" }, "pg": { - "version": "8.4.1", - "resolved": "https://registry.npmjs.org/pg/-/pg-8.4.1.tgz", - "integrity": "sha512-NRsH0aGMXmX1z8Dd0iaPCxWUw4ffu+lIAmGm+sTCwuDDWkpEgRCAHZYDwqaNhC5hG5DRMOjSUFasMWhvcmLN1A==", + "version": "8.4.2", + "resolved": "https://registry.npmjs.org/pg/-/pg-8.4.2.tgz", + "integrity": "sha512-E9FlUrrc7w3+sbRmL1CSw99vifACzB2TjhMM9J5w9D1LIg+6un0jKkpHS1EQf2CWhKhec2bhrBLVMmUBDbjPRQ==", "requires": { "buffer-writer": "2.0.0", "packet-reader": "1.0.0", "pg-connection-string": "^2.4.0", - "pg-pool": "^3.2.1", + "pg-pool": "^3.2.2", "pg-protocol": "^1.3.0", "pg-types": "^2.1.0", "pgpass": "1.x" @@ -810,9 +1043,9 @@ "integrity": "sha512-WCtabS6t3c8SkpDBUlb1kjOs7l66xsGdKpIPZsg4wR+B3+u9UAum2odSsF9tnvxg80h4ZxLWMy4pRjOsFIqQpw==" }, "pg-pool": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/pg-pool/-/pg-pool-3.2.1.tgz", - "integrity": "sha512-BQDPWUeKenVrMMDN9opfns/kZo4lxmSWhIqo+cSAF7+lfi9ZclQbr9vfnlNaPr8wYF3UYjm5X0yPAhbcgqNOdA==" + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/pg-pool/-/pg-pool-3.2.2.tgz", + "integrity": "sha512-ORJoFxAlmmros8igi608iVEbQNNZlp89diFVx6yV5v+ehmpMY9sK6QgpmgoXbmkNaBAx8cOOZh9g80kJv1ooyA==" }, "pg-protocol": { "version": "1.3.0", @@ -909,13 +1142,17 @@ } }, "readable-stream": { - "version": "3.6.0", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", - "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", + "version": "2.3.7", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.7.tgz", + "integrity": "sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==", "requires": { - "inherits": "^2.0.3", - "string_decoder": "^1.1.1", - "util-deprecate": "^1.0.1" + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" } }, "retry-as-promised": { @@ -950,9 +1187,9 @@ "integrity": "sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw==" }, "semver": { - "version": "7.3.2", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.2.tgz", - "integrity": "sha512-OrOb32TeeambH6UrhtShmF7CRDqhL6/5XpPNp2DuRH6+9QLw/orhp72j87v8Qa1ScDkvrrBNpZcDejAirJmfXQ==" + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==" }, "send": { "version": "0.17.1", @@ -974,6 +1211,21 @@ "statuses": "~1.5.0" }, "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "requires": { + "ms": "2.0.0" + }, + "dependencies": { + "ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" + } + } + }, "ms": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.1.tgz", @@ -1009,10 +1261,10 @@ "ms": "2.1.2" } }, - "ms": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" + "semver": { + "version": "7.3.2", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.2.tgz", + "integrity": "sha512-OrOb32TeeambH6UrhtShmF7CRDqhL6/5XpPNp2DuRH6+9QLw/orhp72j87v8Qa1ScDkvrrBNpZcDejAirJmfXQ==" } } }, @@ -1053,6 +1305,18 @@ "integrity": "sha512-9NThjpgZnifTkJpzTZ7Eue85S49QwpNhZTq6GRJwObb6jnLFNGB7Qm73V5HewTROPyxD0C29xqmaI68bQtV+hg==", "requires": { "readable-stream": "^3.0.0" + }, + "dependencies": { + "readable-stream": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", + "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", + "requires": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + } + } } }, "statuses": { @@ -1071,18 +1335,11 @@ } }, "string_decoder": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", - "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", "requires": { - "safe-buffer": "~5.2.0" - }, - "dependencies": { - "safe-buffer": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", - "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==" - } + "safe-buffer": "~5.1.0" } }, "strip-ansi": { diff --git a/package.json b/server/package.json similarity index 57% rename from package.json rename to server/package.json index 1da84d2..5e22e56 100644 --- a/package.json +++ b/server/package.json @@ -1,29 +1,23 @@ { "name": "fancytodo", "version": "1.0.0", - "description": "Todo App", - "main": "app.js", + "description": "ToDo App", + "main": "index.js", "scripts": { "test": "echo \"Error: no test specified\" && exit 1", "dev": "nodemon app.js" }, - "repository": { - "type": "git", - "url": "git+https://github.com/torianyap/FancyTodo.git" - }, "keywords": [], "author": "torianyap", "license": "ISC", - "bugs": { - "url": "https://github.com/torianyap/FancyTodo/issues" - }, - "homepage": "https://github.com/torianyap/FancyTodo#readme", "dependencies": { "axios": "^0.21.0", "bcrypt": "^5.0.0", + "cors": "^2.8.5", "express": "^4.17.1", + "google-auth-library": "^6.1.3", "jsonwebtoken": "^8.5.1", - "pg": "^8.4.1", + "pg": "^8.4.2", "sequelize": "^6.3.5" }, "devDependencies": { diff --git a/server/routes/calendarRoute.js b/server/routes/calendarRoute.js deleted file mode 100644 index 7923c97..0000000 --- a/server/routes/calendarRoute.js +++ /dev/null @@ -1,6 +0,0 @@ -const route = require('express').Router() -const CalendarController = require('../controllers/calendarController') - -route.get('/:country', CalendarController.showHolidays) - -module.exports = route \ No newline at end of file diff --git a/server/routes/index.js b/server/routes/index.js index f647261..d7737c4 100644 --- a/server/routes/index.js +++ b/server/routes/index.js @@ -1,12 +1,10 @@ const route = require('express').Router() const todoRoute = require('./todoRoute') const userRoute = require('./userRoute') -const calendarRoute = require('./calendarRoute') const weatherRoute = require('./weatherRoute') route.use('/todos', todoRoute) route.use('/users', userRoute) -route.use('/holidays', calendarRoute) route.use('/weathers', weatherRoute) module.exports = route \ No newline at end of file diff --git a/server/routes/userRoute.js b/server/routes/userRoute.js index e55e04a..3ad946c 100644 --- a/server/routes/userRoute.js +++ b/server/routes/userRoute.js @@ -3,5 +3,6 @@ const UserController = require('../controllers/userController') route.post('/register', UserController.register) route.post('/login', UserController.login) +route.post('/googleLogin', UserController.googleLogin) module.exports = route \ No newline at end of file From 58be76b63f358ed90474c72f421ab02e5ed65ed9 Mon Sep 17 00:00:00 2001 From: torianyap Date: Wed, 28 Oct 2020 19:34:53 +0700 Subject: [PATCH 13/22] revisi update --- client/convertDate.js | 13 +++++++++++++ client/index.html | 21 +++++---------------- client/index.js | 42 ++++++++++++++++++++++++++++++++++++++---- 3 files changed, 56 insertions(+), 20 deletions(-) create mode 100644 client/convertDate.js diff --git a/client/convertDate.js b/client/convertDate.js new file mode 100644 index 0000000..9102d52 --- /dev/null +++ b/client/convertDate.js @@ -0,0 +1,13 @@ +function formatDate(date) { + var d = new Date(date), + month = '' + (d.getMonth() + 1), + day = '' + d.getDate(), + year = d.getFullYear(); + + if (month.length < 2) + month = '0' + month; + if (day.length < 2) + day = '0' + day; + + return [year, month, day].join('-'); +} \ No newline at end of file diff --git a/client/index.html b/client/index.html index aed4152..aa37dcf 100644 --- a/client/index.html +++ b/client/index.html @@ -75,6 +75,7 @@

Here Are Your ToDo list

+ + + + + - + + + \ No newline at end of file diff --git a/client/index.js b/client/index.js index fa178d4..a701a4b 100644 --- a/client/index.js +++ b/client/index.js @@ -1,11 +1,28 @@ const SERVER = 'http://localhost:3000' +const Toast = Swal.mixin({ + toast: true, + position: "top-end", + showConfirmButton: false, + timer: 3000, + timerProgressBar: true, + didOpen: (toast) => { + toast.addEventListener("mouseenter", Swal.stopTimer); + toast.addEventListener("mouseleave", Swal.resumeTimer); + }, +}); + function beforeLogin() { $('#register').hide() + $('#nav-login').show() + $('#nav-register').show() + $('#nav-name').hide() + $('#nav-logout').hide() $('#login').show() $('#content').hide() $('todos').hide() $('#form-addToDo').hide() + $('#weather').hide() $('#form-updateTodo').hide() } @@ -13,12 +30,22 @@ function afterLogin() { $('#register').hide() $('#login').hide() $('#content').show() + $('#todos').show() + $('#nav-login').hide() + $('#nav-name').empty() + $('#nav-name').append(`${localStorage.getItem('name')}`) + $('#nav-name').show() + $('#nav-register').hide() + $('#nav-logout').show() $('#form-addToDo').hide() $('#form-updateTodo').hide() + $('#weather').show() + $('#weather').empty() fetchToDos() + weather() } -$(document).ready( _ => { +$(document).ready(_ => { const token = localStorage.getItem('access_token') if (token) { afterLogin() @@ -27,6 +54,13 @@ $(document).ready( _ => { } }) +$('#nav-name').on('click', () => { + afterLogin() +}) +$('.back-btn').on('click', () => { + afterLogin() +}) + //move to login $('#nav-login').on('click', () => { $('#register').hide() @@ -34,6 +68,12 @@ $('#nav-login').on('click', () => { $('#content').hide() }) +$('#login-sc').on('click', () => { + $('#register').hide() + $('#login').show() + $('#content').hide() +}) + //move to register $('#nav-register').on('click', () => { $('#register').show() @@ -41,6 +81,12 @@ $('#nav-register').on('click', () => { $('#content').hide() }) +$('#register-sc').on('click', () => { + $('#register').show() + $('#login').hide() + $('#content').hide() +}) + //register const register = e => { e.preventDefault() @@ -48,21 +94,31 @@ const register = e => { const password = $('#register-pwd').val() $.ajax({ - method: 'POST', - url: `${SERVER}/users/register`, - data: { - email, - password - } - }) - .done(response => { - $('#register').hide() - $('#login').show() - $('#todo').hide() - }) - .fail(err => { - console.log(err) - }) + method: 'POST', + url: `${SERVER}/users/register`, + data: { + email, + password + } + }) + .done(response => { + $('#register').hide() + $('#login').show() + $('#todo').hide() + + Swal.fire({ + icon: 'success', + title: 'Sucess', + text: 'Your account has been registered' + }) + }) + .fail(err => { + Swal.fire({ + icon: 'error', + title: 'Error', + text: err.responseJSON.msg + }) + }) } //login @@ -73,238 +129,320 @@ const login = e => { const password = $('#login-pwd').val() $.ajax({ - method: 'POST', - url: `${SERVER}/users/login`, - data: { - email, - password - } - }) - .done(response => { - $('#register').hide() - $('#login').hide() - $('#todo').show() - const access_token = response.accessToken + method: 'POST', + url: `${SERVER}/users/login`, + data: { + email, + password + } + }) + .done(response => { + $('#nav-name').empty() + localStorage.setItem('name', email.substring(0, email.indexOf('@'))) + const access_token = response.accessToken + localStorage.setItem('access_token', access_token) + afterLogin() - localStorage.setItem('access_token', access_token) - fetchToDos() - }) - .fail(err => { - console.log(err) - }) + Toast.fire({ + icon: 'success', + title: 'Logged in successfully' + }) + }) + .fail(err => { + Swal.fire({ + icon: 'error', + title: 'Error', + text: err.responseJSON.msg + }) + }) } function onSignIn(googleUser) { + const profile = googleUser.getBasicProfile(); + const name = profile.gV const google_access_token = googleUser.getAuthResponse().id_token; + $.ajax({ - method:'POST', - url: `${SERVER}/users/googleLogin`, - data: { - google_access_token - } - }) - .done(response => { - localStorage.setItem('access_token', response.access_token) - afterLogin() - }) - .fail(err => { - console.log(err) - }) + method: 'POST', + url: `${SERVER}/users/googleLogin`, + data: { + google_access_token + } + }) + .done(response => { + localStorage.setItem('access_token', response.access_token) + localStorage.setItem('name',name) + $('#nav-name').empty() + afterLogin() + + Toast.fire({ + icon: 'success', + title: 'Logged in successfully' + }) + + }) + .fail(err => { + console.log(err) + }) } //logout $('#nav-logout').on('click', () => { beforeLogin() - localStorage.removeItem('access_token') + localStorage.clear() signOut() + Swal.fire({ + icon: 'info', + title: 'Successfully logged out' + }) }) function signOut() { const auth2 = gapi.auth2.getAuthInstance(); auth2.signOut().then(function () { - console.log('User signed out.'); - } -)}; + console.log('User signed out.'); + }) +}; -//readAll -const fetchToDos = () => { - const access_token = localStorage.getItem('access_token') - $('#todos').empty() +//Weather +const weather = () => { + $('#weather').empty() $.ajax({ method: 'GET', - url: `${SERVER}/todos`, - headers : { - access_token: access_token - } + url: `${SERVER}/weathers` }) .done(response => { console.log(response) - if (response[0]) { - response.forEach(el => { - if(el.status === false) { - $('#todos').append(` -

${el.title.toUpperCase()}

-

${el.description}

-

${new Date(el.due_date)}

- Finish - - -
- `) - } else { - $('#todos').append(` -

${el.title.toUpperCase()}

-

${el.description}

-

${new Date(el.due_date)}

- Finish - -
- `) - } - }) - } else { - $('#todos').append(`
There's nothing here
Start adding some task
`) - } + $('#weather').append(` +
Current Weather
+

Place +
${response.name}

+ +

Description +
${response.weather[0].main} + weather-icon

+ +

Temperature +
Temperature: ${response.main.temp.toFixed(1)}°C +
Feels Like: ${response.main.feels_like.toFixed(1)}°C

+ +

Humidity +
${response.main.humidity}%

+ `) }) .fail(err => { - console.log(err) + Toast.fire({ + icon: 'warning', + title: `i can't find your location` + }) }) } +//fetchTodos +const fetchToDos = () => { + const access_token = localStorage.getItem('access_token') + $('#todos').empty() + $.ajax({ + method: 'GET', + url: `${SERVER}/todos`, + headers: { + access_token: access_token + } + }) + .done(response => { + if (response[0]) { + response.forEach(el => { + if (el.status === false) { + $('#todos').append(` +
+
+
${el.title}
+
+ ${el.description}

+ Due at: ${formatDate(el.due_date)} +
+
+

+ Finish Task
+ Update Task + Delete Task +

+
+
`) + } else { + $('#todos').append(` +
+
+
${el.title}
+
+ ${el.description}

+ Due at: ${formatDate(el.due_date)} +
+
+

+ Task Finished
+ Delete Task +

+
+
`) + } + }) + } else { + $('#todos').append(` +
There's nothing here
Start adding some task
`) + } + }) + .fail(err => { + Swal.fire({ + icon: 'error', + title: err.responseJSON.msg + }) + }) +} + //addTodo const addTodo = () => { const access_token = localStorage.getItem('access_token') - const title = $('#title').val() - const description = $('#description').val() - const due_date = $('#due_date').val() + const title = $('#add_title').val() + const description = $('#add_description').val() + const due_date = $('#add_due_date').val() $.ajax({ - method: 'POST', - url: `${SERVER}/todos`, - data: { - title, - description, - due_date - }, - headers: { - access_token - } - }) - .done(response => { - afterLogin() + method: 'POST', + url: `${SERVER}/todos`, + data: { + title, + description, + due_date + }, + headers: { + access_token + } + }) + .done(response => { + afterLogin() + Toast.fire({ + icon: 'success', + title: 'ToDo added successfully' + }) - }) - .fail(err => { - console.log(err) - }) + }) + .fail(err => { + Swal.fire({ + icon: 'error', + title: 'Error', + text: err.responseJSON.msg + }) + }) + .always(() => { + $('#add_title').val("") + $('#add_description').val("") + $('#add_due_date').val("") + }) } $('#addTodo').on('click', () => { + $('#todos').hide() $('#form-addToDo').show() $('#form-updateTodo').hide() }) //updateTodo -let goingToBeUpdated; +let idTemp; -const updateToDo = id => { - id = goingToBeUpdated.id +const updateToDo = _ => { const access_token = localStorage.getItem('access_token') - const title = $('#update_title').val() - const description = $('#update_description').val() - const due_date = $('#update_due_date').val() + const title = $('#edit_title').val() + const description = $('#edit_description').val() + const due_date = $('#edit_due_date').val() $.ajax({ - method: 'PUT', - url: `${SERVER}/todos/${id}`, - headers: { - access_token: access_token - }, - data: { - title, - description, - due_date - } - }) - .done(response => { - afterLogin() - }) - .fail(err => { - console.log(err) - }) + method: 'PUT', + url: `${SERVER}/todos/${idTemp}`, + headers: { + access_token: access_token + }, + data: { + title, + description, + due_date + } + }) + .done(response => { + afterLogin() + Toast.fire({ + icon: 'success', + title: `${response.title} has been updated` + }) + }) + .fail(err => { + Swal.fire({ + icon: 'error', + title: 'Error', + text: err.responseJSON.msg + }) + }) } -const updateToDoForm = (id) => { - const access_token = localStorage.getItem('access_token') - - $.ajax({ - method: 'GET', - url: `${SERVER}/todos/${id}`, - headers: { - access_token - } - }) - .done(response => { - $('#form-updateTodo').append(` -
-
- - -
-
- - -
-
- - - due date must be greater than today -
- -
- `) - }) - +const updateToDoForm = (id, title, description, due_date) => { + afterLogin() $('#form-updateTodo').show() - $('#form-addToDo').hide() - .fail(err => { - console.log(err) - }) + $('#edit_title').val(title) + $('#edit_description').val(description) + $('#edit_due_date').val(formatDate(due_date)) + idTemp = id + } //finishTodo const finishToDo = id => { const access_token = localStorage.getItem('access_token') $.ajax({ - method: 'PATCH', - url: `${SERVER}/todos/${id}`, - headers: { - access_token: access_token - } - }) - .done(response => { - afterLogin() - }) - .fail(err => { - console.log(err) - }) + method: 'PATCH', + url: `${SERVER}/todos/${id}`, + headers: { + access_token: access_token + } + }) + .done(response => { + afterLogin() + Toast.fire({ + icon: 'success', + title: `you have finished todo ${response.title}` + }) + }) + .fail(err => { + Swal.fire({ + icon: 'error', + title: 'Error', + text: err.responseJSON.msg + }) + }) } //deleteToDo const deleteToDo = id => { const access_token = localStorage.getItem('access_token') $.ajax({ - method: 'DELETE', - url: `${SERVER}/todos/${id}`, - headers: { - access_token: access_token - } - }) - .done(response => { - afterLogin() - }) - .fail(err => { - console.log(err) - }) + method: 'DELETE', + url: `${SERVER}/todos/${id}`, + headers: { + access_token: access_token + } + }) + .done(response => { + afterLogin() + Toast.fire({ + icon: 'success', + title: 'todo successfully deleted' + }) + }) + .fail(err => { + Swal.fire({ + icon: 'error', + title: 'Error', + text: err.responseJSON.msg + }) + }) } \ No newline at end of file diff --git a/client/style.css b/client/style.css new file mode 100644 index 0000000..954ab4c --- /dev/null +++ b/client/style.css @@ -0,0 +1,45 @@ +html, +body { + height: 100%; +} + +body { + display: -ms-flexbox; + display: flex; + -ms-flex-align: center; + align-items: center; + padding-top: 40px; + padding-bottom: 40px; + background-color: #f5f5f5; + font-family: 'Prompt', sans-serif; +} + +.form-signin { + width: 100%; + max-width: 330px; + padding: 15px; + margin: auto; +} +.form-signin .checkbox { + font-weight: 400; +} +.form-signin .form-control { + position: relative; + box-sizing: border-box; + height: auto; + padding: 10px; + font-size: 16px; +} +.form-signin .form-control:focus { + z-index: 2; +} +.form-signin input[type="email"] { + margin-bottom: -1px; + border-bottom-right-radius: 0; + border-bottom-left-radius: 0; +} +.form-signin input[type="password"] { + margin-bottom: 10px; + border-top-left-radius: 0; + border-top-right-radius: 0; +} \ No newline at end of file diff --git a/server/controllers/userController.js b/server/controllers/userController.js index 90651da..2691cc0 100644 --- a/server/controllers/userController.js +++ b/server/controllers/userController.js @@ -12,7 +12,7 @@ class UserController { } const user = await User.create(payload) - res.status(200).json({ + res.status(201).json({ id: user.id, email: user.email }) diff --git a/server/controllers/weatherController.js b/server/controllers/weatherController.js index 8f274ec..e5bbb46 100644 --- a/server/controllers/weatherController.js +++ b/server/controllers/weatherController.js @@ -1,19 +1,31 @@ -const axios = require('axios') +const axios = require('axios') class WeatherController { static currentWeather (req, res, next) { - const q = req.params.city // e.g: Jakarta,id / London / Brazil / dll axios({ - url: `http://api.openweathermap.org/data/2.5/weather?q=${q}&appid=${process.env.WEATHER}`, - method: 'get' + method: 'GET', + url: 'https://api.ipgeolocation.io/getip' }) - .then(result => { - res.status(200).json(result.data) + .then(response => { + const ip = response.data.ip + return axios({ + method: 'GET', + url: `https://api.ipgeolocation.io/astronomy?apiKey=${process.env.GEO}&ip=${ip}` + }) + }) + .then(result => { + const city = result.data.location.state_prov + return axios({ + url: `http://api.openweathermap.org/data/2.5/weather?q=${city}&appid=${process.env.WEATHER}&units=metric`, + method: 'GET' + }) + }) + .then(data => { + res.status(200).json(data.data) }) .catch(err => { next(err) }) } } - module.exports = WeatherController \ No newline at end of file diff --git a/server/models/user.js b/server/models/user.js index f04fe35..88b3d7c 100644 --- a/server/models/user.js +++ b/server/models/user.js @@ -45,8 +45,8 @@ module.exports = (sequelize, DataTypes) => { msg: `password must be alphanumeric` }, len: { - args: [5,20], - msg: `password must be a minimal of 5 and a maximum of 20 characters` + args: [6,20], + msg: `password must be a minimal of 6 and a maximum of 20 characters` } } } diff --git a/server/package-lock.json b/server/package-lock.json index 894f1fd..e772015 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -290,6 +290,19 @@ "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", "integrity": "sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=" }, + "es6-promise": { + "version": "4.2.8", + "resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-4.2.8.tgz", + "integrity": "sha512-HJDGx5daxeIvxdBxvG2cb9g4tEvwIk3i8+nhX0yGrYmZUzbkdg8QbDevheDB8gd0//uPj4c1EQua8Q+MViT0/w==" + }, + "es6-promisify": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/es6-promisify/-/es6-promisify-5.0.0.tgz", + "integrity": "sha1-UQnWLz5W6pZ8S2NQWu8IKRyKUgM=", + "requires": { + "es6-promise": "^4.0.3" + } + }, "escape-html": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", @@ -532,6 +545,237 @@ "node-forge": "^0.10.0" } }, + "googleapis": { + "version": "39.2.0", + "resolved": "https://registry.npmjs.org/googleapis/-/googleapis-39.2.0.tgz", + "integrity": "sha512-66X8TG1B33zAt177sG1CoKoYHPP/B66tEpnnSANGCqotMuY5gqSQO8G/0gqHZR2jRgc5CHSSNOJCnpI0SuDxMQ==", + "requires": { + "google-auth-library": "^3.0.0", + "googleapis-common": "^0.7.0" + }, + "dependencies": { + "agent-base": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-4.3.0.tgz", + "integrity": "sha512-salcGninV0nPrwpGNn4VTXBb1SOuXQBiqbrNXoeizJsHrsL6ERFM2Ne3JUSBWRE6aeNJI2ROP/WEEIDUiDe3cg==", + "requires": { + "es6-promisify": "^5.0.0" + } + }, + "gaxios": { + "version": "1.8.4", + "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-1.8.4.tgz", + "integrity": "sha512-BoENMnu1Gav18HcpV9IleMPZ9exM+AvUjrAOV4Mzs/vfz2Lu/ABv451iEXByKiMPn2M140uul1txXCg83sAENw==", + "requires": { + "abort-controller": "^3.0.0", + "extend": "^3.0.2", + "https-proxy-agent": "^2.2.1", + "node-fetch": "^2.3.0" + } + }, + "gcp-metadata": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/gcp-metadata/-/gcp-metadata-1.0.0.tgz", + "integrity": "sha512-Q6HrgfrCQeEircnNP3rCcEgiDv7eF9+1B+1MMgpE190+/+0mjQR8PxeOaRgxZWmdDAF9EIryHB9g1moPiw1SbQ==", + "requires": { + "gaxios": "^1.0.2", + "json-bigint": "^0.3.0" + } + }, + "google-auth-library": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-3.1.2.tgz", + "integrity": "sha512-cDQMzTotwyWMrg5jRO7q0A4TL/3GWBgO7I7q5xGKNiiFf9SmGY/OJ1YsLMgI2MVHHsEGyrqYnbnmV1AE+Z6DnQ==", + "requires": { + "base64-js": "^1.3.0", + "fast-text-encoding": "^1.0.0", + "gaxios": "^1.2.1", + "gcp-metadata": "^1.0.0", + "gtoken": "^2.3.2", + "https-proxy-agent": "^2.2.1", + "jws": "^3.1.5", + "lru-cache": "^5.0.0", + "semver": "^5.5.0" + } + }, + "google-p12-pem": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/google-p12-pem/-/google-p12-pem-1.0.4.tgz", + "integrity": "sha512-SwLAUJqUfTB2iS+wFfSS/G9p7bt4eWcc2LyfvmUXe7cWp6p3mpxDo6LLI29MXdU6wvPcQ/up298X7GMC5ylAlA==", + "requires": { + "node-forge": "^0.8.0", + "pify": "^4.0.0" + } + }, + "gtoken": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-2.3.3.tgz", + "integrity": "sha512-EaB49bu/TCoNeQjhCYKI/CurooBKkGxIqFHsWABW0b25fobBYVTMe84A8EBVVZhl8emiUdNypil9huMOTmyAnw==", + "requires": { + "gaxios": "^1.0.4", + "google-p12-pem": "^1.0.0", + "jws": "^3.1.5", + "mime": "^2.2.0", + "pify": "^4.0.0" + } + }, + "https-proxy-agent": { + "version": "2.2.4", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-2.2.4.tgz", + "integrity": "sha512-OmvfoQ53WLjtA9HeYP9RNrWMJzzAz1JGaSFr1nijg0PVR1JaD/xbJq1mdEIIlxGpXp9eSe/O2LgU9DJmTPd0Eg==", + "requires": { + "agent-base": "^4.3.0", + "debug": "^3.1.0" + } + }, + "json-bigint": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/json-bigint/-/json-bigint-0.3.1.tgz", + "integrity": "sha512-DGWnSzmusIreWlEupsUelHrhwmPPE+FiQvg+drKfk2p+bdEYa5mp4PJ8JsCWqae0M2jQNb0HPvnwvf1qOTThzQ==", + "requires": { + "bignumber.js": "^9.0.0" + } + }, + "lru-cache": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", + "integrity": "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==", + "requires": { + "yallist": "^3.0.2" + } + }, + "mime": { + "version": "2.4.6", + "resolved": "https://registry.npmjs.org/mime/-/mime-2.4.6.tgz", + "integrity": "sha512-RZKhC3EmpBchfTGBVb8fb+RL2cWyw/32lshnsETttkBAyAUXSGHxbEJWWRXc751DrIxG1q04b8QwMbAwkRPpUA==" + }, + "node-forge": { + "version": "0.8.5", + "resolved": "https://registry.npmjs.org/node-forge/-/node-forge-0.8.5.tgz", + "integrity": "sha512-vFMQIWt+J/7FLNyKouZ9TazT74PRV3wgv9UT4cRjC8BffxFbKXkgIWR42URCPSnHm/QDz6BOlb2Q0U4+VQT67Q==" + } + } + }, + "googleapis-common": { + "version": "0.7.2", + "resolved": "https://registry.npmjs.org/googleapis-common/-/googleapis-common-0.7.2.tgz", + "integrity": "sha512-9DEJIiO4nS7nw0VE1YVkEfXEj8x8MxsuB+yZIpOBULFSN9OIKcUU8UuKgSZFU4lJmRioMfngktrbkMwWJcUhQg==", + "requires": { + "gaxios": "^1.2.2", + "google-auth-library": "^3.0.0", + "pify": "^4.0.0", + "qs": "^6.5.2", + "url-template": "^2.0.8", + "uuid": "^3.2.1" + }, + "dependencies": { + "agent-base": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-4.3.0.tgz", + "integrity": "sha512-salcGninV0nPrwpGNn4VTXBb1SOuXQBiqbrNXoeizJsHrsL6ERFM2Ne3JUSBWRE6aeNJI2ROP/WEEIDUiDe3cg==", + "requires": { + "es6-promisify": "^5.0.0" + } + }, + "gaxios": { + "version": "1.8.4", + "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-1.8.4.tgz", + "integrity": "sha512-BoENMnu1Gav18HcpV9IleMPZ9exM+AvUjrAOV4Mzs/vfz2Lu/ABv451iEXByKiMPn2M140uul1txXCg83sAENw==", + "requires": { + "abort-controller": "^3.0.0", + "extend": "^3.0.2", + "https-proxy-agent": "^2.2.1", + "node-fetch": "^2.3.0" + } + }, + "gcp-metadata": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/gcp-metadata/-/gcp-metadata-1.0.0.tgz", + "integrity": "sha512-Q6HrgfrCQeEircnNP3rCcEgiDv7eF9+1B+1MMgpE190+/+0mjQR8PxeOaRgxZWmdDAF9EIryHB9g1moPiw1SbQ==", + "requires": { + "gaxios": "^1.0.2", + "json-bigint": "^0.3.0" + } + }, + "google-auth-library": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-3.1.2.tgz", + "integrity": "sha512-cDQMzTotwyWMrg5jRO7q0A4TL/3GWBgO7I7q5xGKNiiFf9SmGY/OJ1YsLMgI2MVHHsEGyrqYnbnmV1AE+Z6DnQ==", + "requires": { + "base64-js": "^1.3.0", + "fast-text-encoding": "^1.0.0", + "gaxios": "^1.2.1", + "gcp-metadata": "^1.0.0", + "gtoken": "^2.3.2", + "https-proxy-agent": "^2.2.1", + "jws": "^3.1.5", + "lru-cache": "^5.0.0", + "semver": "^5.5.0" + } + }, + "google-p12-pem": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/google-p12-pem/-/google-p12-pem-1.0.4.tgz", + "integrity": "sha512-SwLAUJqUfTB2iS+wFfSS/G9p7bt4eWcc2LyfvmUXe7cWp6p3mpxDo6LLI29MXdU6wvPcQ/up298X7GMC5ylAlA==", + "requires": { + "node-forge": "^0.8.0", + "pify": "^4.0.0" + } + }, + "gtoken": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-2.3.3.tgz", + "integrity": "sha512-EaB49bu/TCoNeQjhCYKI/CurooBKkGxIqFHsWABW0b25fobBYVTMe84A8EBVVZhl8emiUdNypil9huMOTmyAnw==", + "requires": { + "gaxios": "^1.0.4", + "google-p12-pem": "^1.0.0", + "jws": "^3.1.5", + "mime": "^2.2.0", + "pify": "^4.0.0" + } + }, + "https-proxy-agent": { + "version": "2.2.4", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-2.2.4.tgz", + "integrity": "sha512-OmvfoQ53WLjtA9HeYP9RNrWMJzzAz1JGaSFr1nijg0PVR1JaD/xbJq1mdEIIlxGpXp9eSe/O2LgU9DJmTPd0Eg==", + "requires": { + "agent-base": "^4.3.0", + "debug": "^3.1.0" + } + }, + "json-bigint": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/json-bigint/-/json-bigint-0.3.1.tgz", + "integrity": "sha512-DGWnSzmusIreWlEupsUelHrhwmPPE+FiQvg+drKfk2p+bdEYa5mp4PJ8JsCWqae0M2jQNb0HPvnwvf1qOTThzQ==", + "requires": { + "bignumber.js": "^9.0.0" + } + }, + "lru-cache": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", + "integrity": "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==", + "requires": { + "yallist": "^3.0.2" + } + }, + "mime": { + "version": "2.4.6", + "resolved": "https://registry.npmjs.org/mime/-/mime-2.4.6.tgz", + "integrity": "sha512-RZKhC3EmpBchfTGBVb8fb+RL2cWyw/32lshnsETttkBAyAUXSGHxbEJWWRXc751DrIxG1q04b8QwMbAwkRPpUA==" + }, + "node-forge": { + "version": "0.8.5", + "resolved": "https://registry.npmjs.org/node-forge/-/node-forge-0.8.5.tgz", + "integrity": "sha512-vFMQIWt+J/7FLNyKouZ9TazT74PRV3wgv9UT4cRjC8BffxFbKXkgIWR42URCPSnHm/QDz6BOlb2Q0U4+VQT67Q==" + }, + "uuid": { + "version": "3.4.0", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", + "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==" + } + } + }, "gtoken": { "version": "5.0.5", "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-5.0.5.tgz", @@ -1072,6 +1316,11 @@ "split2": "^3.1.1" } }, + "pify": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/pify/-/pify-4.0.1.tgz", + "integrity": "sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g==" + }, "postgres-array": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/postgres-array/-/postgres-array-2.0.0.tgz", @@ -1393,6 +1642,11 @@ "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=" }, + "url-template": { + "version": "2.0.8", + "resolved": "https://registry.npmjs.org/url-template/-/url-template-2.0.8.tgz", + "integrity": "sha1-/FZaPMy/93MMd19WQflVV5FDnyE=" + }, "util-deprecate": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", diff --git a/server/package.json b/server/package.json index 5e22e56..379bf23 100644 --- a/server/package.json +++ b/server/package.json @@ -16,6 +16,7 @@ "cors": "^2.8.5", "express": "^4.17.1", "google-auth-library": "^6.1.3", + "googleapis": "^39.2.0", "jsonwebtoken": "^8.5.1", "pg": "^8.4.2", "sequelize": "^6.3.5" diff --git a/server/routes/weatherRoute.js b/server/routes/weatherRoute.js index ceca306..2877a81 100644 --- a/server/routes/weatherRoute.js +++ b/server/routes/weatherRoute.js @@ -1,6 +1,6 @@ const route = require('express').Router() const WeatherController = require('../controllers/weatherController') -route.get('/:city', WeatherController.currentWeather) +route.get('/', WeatherController.currentWeather) module.exports = route \ No newline at end of file From 96d9c22d909e72a00eacfbaa945dd48a3f9fd25b Mon Sep 17 00:00:00 2001 From: torianyap Date: Sun, 1 Nov 2020 10:56:08 +0700 Subject: [PATCH 15/22] add confirmation delete and logout --- client/index.js | 92 +++++++++++++++++++++++++++++++++++-------------- 1 file changed, 67 insertions(+), 25 deletions(-) diff --git a/client/index.js b/client/index.js index a701a4b..503dbaa 100644 --- a/client/index.js +++ b/client/index.js @@ -188,14 +188,34 @@ function onSignIn(googleUser) { //logout $('#nav-logout').on('click', () => { - beforeLogin() - - localStorage.clear() - signOut() Swal.fire({ - icon: 'info', - title: 'Successfully logged out' + title: `Logout`, + text: `You're going to be logged out`, + icon: 'warning', + showCancelButton: true, + confirmButtonColor: '#3085d6', + cancelButtonColor: '#d33', + confirmButtonText: 'Logout' + }) + .then((result) => { + if (result.isConfirmed) { + Swal.fire({ + icon: 'info', + title: 'Successfully logged out' + }) + beforeLogin() + localStorage.clear() + signOut() + + } else { + Toast.fire({ + icon: 'info', + title: 'cancelled' + }) + afterLogin() + } }) + }) function signOut() { @@ -236,6 +256,7 @@ const weather = () => { icon: 'warning', title: `i can't find your location` }) + $('#weather').hide() }) } @@ -424,25 +445,46 @@ const finishToDo = id => { //deleteToDo const deleteToDo = id => { const access_token = localStorage.getItem('access_token') - $.ajax({ - method: 'DELETE', - url: `${SERVER}/todos/${id}`, - headers: { - access_token: access_token - } - }) - .done(response => { - afterLogin() - Toast.fire({ - icon: 'success', - title: 'todo successfully deleted' + + Swal.fire({ + title: `Delete Task`, + text: `You're going to delete this task`, + icon: 'warning', + showCancelButton: true, + confirmButtonColor: '#3085d6', + cancelButtonColor: '#d33', + confirmButtonText: 'Delete' + }) + .then((result) => { + if (result.isConfirmed) { + $.ajax({ + method: 'DELETE', + url: `${SERVER}/todos/${id}`, + headers: { + access_token: access_token + } }) - }) - .fail(err => { - Swal.fire({ - icon: 'error', - title: 'Error', - text: err.responseJSON.msg + .done(response => { + afterLogin() + Toast.fire({ + icon: 'success', + title: 'todo successfully deleted' + }) }) - }) + .fail(err => { + Swal.fire({ + icon: 'error', + title: 'Error', + text: err.responseJSON.msg + }) + }) + + } else { + Toast.fire({ + icon: 'info', + title: 'cancelled' + }) + afterLogin() + } + }) } \ No newline at end of file From 4c7c51a14eb5f195c28974a9357b80451e5b4e58 Mon Sep 17 00:00:00 2001 From: torianyap Date: Sun, 1 Nov 2020 11:03:08 +0700 Subject: [PATCH 16/22] minor changes --- client/index.html | 2 -- client/index.js | 6 ++++++ 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/client/index.html b/client/index.html index 970f488..103db6e 100644 --- a/client/index.html +++ b/client/index.html @@ -10,8 +10,6 @@ - - diff --git a/client/index.js b/client/index.js index 503dbaa..9cd44d6 100644 --- a/client/index.js +++ b/client/index.js @@ -119,6 +119,9 @@ const register = e => { text: err.responseJSON.msg }) }) + .always(() => { + $('#register-pwd').val("") + }) } //login @@ -155,6 +158,9 @@ const login = e => { text: err.responseJSON.msg }) }) + .always(() => { + $('#login-pwd').val("") + }) } function onSignIn(googleUser) { From ae90d32db36a10d4fb9079bde7ce7948bbb5a3b5 Mon Sep 17 00:00:00 2001 From: torianyap Date: Sun, 1 Nov 2020 11:12:50 +0700 Subject: [PATCH 17/22] minor changes --- client/index.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/index.html b/client/index.html index 103db6e..8330aca 100644 --- a/client/index.html +++ b/client/index.html @@ -34,7 +34,7 @@ From 4bf113c0b83fc5fed8bf81934f9127b3a7c79688 Mon Sep 17 00:00:00 2001 From: torianyap Date: Mon, 2 Nov 2020 15:39:42 +0700 Subject: [PATCH 18/22] deploy heroku --- server/app.js | 6 +- server/config/config.json | 6 +- server/helper/bcrypt.js | 2 +- server/package-lock.json | 691 +------------------------------------- server/package.json | 6 +- 5 files changed, 13 insertions(+), 698 deletions(-) diff --git a/server/app.js b/server/app.js index 8629e38..147ee06 100644 --- a/server/app.js +++ b/server/app.js @@ -1,4 +1,6 @@ -require('dotenv').config() +if (process.env.NODE_ENV !== 'production') { + require('dotenv').config() +} const express = require('express') const cors = require('cors') @@ -6,7 +8,7 @@ const router = require('./routes') const error_handler = require('./middlewares/error_handler') const app = express() -const port = process.env.PORT +const port = process.env.PORT || 3000 app.use(cors()) app.use(express.json()) diff --git a/server/config/config.json b/server/config/config.json index 975560e..bebff9b 100644 --- a/server/config/config.json +++ b/server/config/config.json @@ -14,10 +14,6 @@ "dialect": "mysql" }, "production": { - "username": "root", - "password": null, - "database": "database_production", - "host": "127.0.0.1", - "dialect": "mysql" + "use_env_variable": "postgres://ndbaersqegmwbq:52801c4ce7fe42ac0b5a6b21e5783c5cf9a49b89434604186305e97b28cd8d7c@ec2-3-208-224-152.compute-1.amazonaws.com:5432/d2pnr7ord1rot7" } } diff --git a/server/helper/bcrypt.js b/server/helper/bcrypt.js index 94eafdc..0db51e1 100644 --- a/server/helper/bcrypt.js +++ b/server/helper/bcrypt.js @@ -1,4 +1,4 @@ -const bcrypt = require('bcrypt') +const bcrypt = require("bcryptjs") const hashPassword = password => { const hashed = bcrypt.hashSync(password, +process.env.SALT) diff --git a/server/package-lock.json b/server/package-lock.json index e772015..bc6ecf6 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -9,11 +9,6 @@ "resolved": "https://registry.npmjs.org/@types/node/-/node-14.14.5.tgz", "integrity": "sha512-H5Wn24s/ZOukBmDn03nnGTp18A60ny9AmCwnEcgJiTgSGsCO7k+NWP7zjCCbhlcnVCoI+co52dUAt9GMhOSULw==" }, - "abbrev": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz", - "integrity": "sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==" - }, "abort-controller": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/abort-controller/-/abort-controller-3.0.0.tgz", @@ -49,30 +44,11 @@ } } }, - "ansi-regex": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=" - }, "any-promise": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/any-promise/-/any-promise-1.3.0.tgz", "integrity": "sha1-q8av7tzqUugJzcA3au0845Y10X8=" }, - "aproba": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/aproba/-/aproba-1.2.0.tgz", - "integrity": "sha512-Y9J6ZjXtoYh8RnXVCMOU/ttDmk1aBjunq9vO0ta5x85WDQiQfUF9sIPBITdbiiIVcBo03Hi3jMxigBtsddlXRw==" - }, - "are-we-there-yet": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-1.1.5.tgz", - "integrity": "sha512-5hYdAkZlcG8tOLujVDTgCT+uPX0VnpAH28gWsLfzpXYm7wP6mp5Q/gYyR7YQ0cKVJcXJnl3j2kpBan13PtQf6w==", - "requires": { - "delegates": "^1.0.0", - "readable-stream": "^2.0.6" - } - }, "array-flatten": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", @@ -91,24 +67,15 @@ "follow-redirects": "^1.10.0" } }, - "balanced-match": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" - }, "base64-js": { "version": "1.3.1", "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.3.1.tgz", "integrity": "sha512-mLQ4i2QO1ytvGWFWmcngKO//JXAQueZvwEKtjgQFM4jIK0kU+ytMfplL8j+n5mspOfjHwoAg+9yhb7BwAHm36g==" }, - "bcrypt": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/bcrypt/-/bcrypt-5.0.0.tgz", - "integrity": "sha512-jB0yCBl4W/kVHM2whjfyqnxTmOHkCX4kHEa5nYKSoGeYe8YrjTYTc87/6bwt1g8cmV0QrbhKriETg9jWtcREhg==", - "requires": { - "node-addon-api": "^3.0.0", - "node-pre-gyp": "0.15.0" - } + "bcryptjs": { + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/bcryptjs/-/bcryptjs-2.4.3.tgz", + "integrity": "sha1-mrVie5PmBiH/fNrF2pczAn3x0Ms=" }, "bignumber.js": { "version": "9.0.1", @@ -147,15 +114,6 @@ } } }, - "brace-expansion": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", - "requires": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" - } - }, "buffer-equal-constant-time": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz", @@ -171,26 +129,6 @@ "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.0.tgz", "integrity": "sha512-zauLjrfCG+xvoyaqLoV8bLVXXNGC4JqlxFCutSDWA6fJrTo2ZuvLYTqZ7aHBLZSMOopbzwv8f+wZcVzfVTI2Dg==" }, - "chownr": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.1.4.tgz", - "integrity": "sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg==" - }, - "code-point-at": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", - "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=" - }, - "concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" - }, - "console-control-strings": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/console-control-strings/-/console-control-strings-1.1.0.tgz", - "integrity": "sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4=" - }, "content-disposition": { "version": "0.5.3", "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.3.tgz", @@ -214,11 +152,6 @@ "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" }, - "core-util-is": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", - "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" - }, "cors": { "version": "2.8.5", "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", @@ -228,24 +161,6 @@ "vary": "^1" } }, - "debug": { - "version": "3.2.6", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz", - "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==", - "requires": { - "ms": "^2.1.1" - } - }, - "deep-extend": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", - "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==" - }, - "delegates": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz", - "integrity": "sha1-hMbhWbgZBP3KWaDvRM2HDTElD5o=" - }, "depd": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", @@ -256,11 +171,6 @@ "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.0.4.tgz", "integrity": "sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA=" }, - "detect-libc": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-1.0.3.tgz", - "integrity": "sha1-+hN8S9aY7fVc1c0CrFWfkaTEups=" - }, "dotenv": { "version": "8.2.0", "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-8.2.0.tgz", @@ -290,19 +200,6 @@ "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", "integrity": "sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=" }, - "es6-promise": { - "version": "4.2.8", - "resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-4.2.8.tgz", - "integrity": "sha512-HJDGx5daxeIvxdBxvG2cb9g4tEvwIk3i8+nhX0yGrYmZUzbkdg8QbDevheDB8gd0//uPj4c1EQua8Q+MViT0/w==" - }, - "es6-promisify": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/es6-promisify/-/es6-promisify-5.0.0.tgz", - "integrity": "sha1-UQnWLz5W6pZ8S2NQWu8IKRyKUgM=", - "requires": { - "es6-promise": "^4.0.3" - } - }, "escape-html": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", @@ -424,34 +321,6 @@ "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=" }, - "fs-minipass": { - "version": "1.2.7", - "resolved": "https://registry.npmjs.org/fs-minipass/-/fs-minipass-1.2.7.tgz", - "integrity": "sha512-GWSSJGFy4e9GUeCcbIkED+bgAoFyj7XF1mV8rma3QW4NIqX9Kyx79N/PF61H5udOV3aY1IaMLs6pGbH71nlCTA==", - "requires": { - "minipass": "^2.6.0" - } - }, - "fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" - }, - "gauge": { - "version": "2.7.4", - "resolved": "https://registry.npmjs.org/gauge/-/gauge-2.7.4.tgz", - "integrity": "sha1-LANAXHU4w51+s3sxcCLjJfsBi/c=", - "requires": { - "aproba": "^1.0.3", - "console-control-strings": "^1.0.0", - "has-unicode": "^2.0.0", - "object-assign": "^4.1.0", - "signal-exit": "^3.0.0", - "string-width": "^1.0.1", - "strip-ansi": "^3.0.1", - "wide-align": "^1.1.0" - } - }, "gaxios": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-4.0.1.tgz", @@ -487,19 +356,6 @@ } } }, - "glob": { - "version": "7.1.6", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.6.tgz", - "integrity": "sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA==", - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, "google-auth-library": { "version": "6.1.3", "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-6.1.3.tgz", @@ -545,237 +401,6 @@ "node-forge": "^0.10.0" } }, - "googleapis": { - "version": "39.2.0", - "resolved": "https://registry.npmjs.org/googleapis/-/googleapis-39.2.0.tgz", - "integrity": "sha512-66X8TG1B33zAt177sG1CoKoYHPP/B66tEpnnSANGCqotMuY5gqSQO8G/0gqHZR2jRgc5CHSSNOJCnpI0SuDxMQ==", - "requires": { - "google-auth-library": "^3.0.0", - "googleapis-common": "^0.7.0" - }, - "dependencies": { - "agent-base": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-4.3.0.tgz", - "integrity": "sha512-salcGninV0nPrwpGNn4VTXBb1SOuXQBiqbrNXoeizJsHrsL6ERFM2Ne3JUSBWRE6aeNJI2ROP/WEEIDUiDe3cg==", - "requires": { - "es6-promisify": "^5.0.0" - } - }, - "gaxios": { - "version": "1.8.4", - "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-1.8.4.tgz", - "integrity": "sha512-BoENMnu1Gav18HcpV9IleMPZ9exM+AvUjrAOV4Mzs/vfz2Lu/ABv451iEXByKiMPn2M140uul1txXCg83sAENw==", - "requires": { - "abort-controller": "^3.0.0", - "extend": "^3.0.2", - "https-proxy-agent": "^2.2.1", - "node-fetch": "^2.3.0" - } - }, - "gcp-metadata": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/gcp-metadata/-/gcp-metadata-1.0.0.tgz", - "integrity": "sha512-Q6HrgfrCQeEircnNP3rCcEgiDv7eF9+1B+1MMgpE190+/+0mjQR8PxeOaRgxZWmdDAF9EIryHB9g1moPiw1SbQ==", - "requires": { - "gaxios": "^1.0.2", - "json-bigint": "^0.3.0" - } - }, - "google-auth-library": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-3.1.2.tgz", - "integrity": "sha512-cDQMzTotwyWMrg5jRO7q0A4TL/3GWBgO7I7q5xGKNiiFf9SmGY/OJ1YsLMgI2MVHHsEGyrqYnbnmV1AE+Z6DnQ==", - "requires": { - "base64-js": "^1.3.0", - "fast-text-encoding": "^1.0.0", - "gaxios": "^1.2.1", - "gcp-metadata": "^1.0.0", - "gtoken": "^2.3.2", - "https-proxy-agent": "^2.2.1", - "jws": "^3.1.5", - "lru-cache": "^5.0.0", - "semver": "^5.5.0" - } - }, - "google-p12-pem": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/google-p12-pem/-/google-p12-pem-1.0.4.tgz", - "integrity": "sha512-SwLAUJqUfTB2iS+wFfSS/G9p7bt4eWcc2LyfvmUXe7cWp6p3mpxDo6LLI29MXdU6wvPcQ/up298X7GMC5ylAlA==", - "requires": { - "node-forge": "^0.8.0", - "pify": "^4.0.0" - } - }, - "gtoken": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-2.3.3.tgz", - "integrity": "sha512-EaB49bu/TCoNeQjhCYKI/CurooBKkGxIqFHsWABW0b25fobBYVTMe84A8EBVVZhl8emiUdNypil9huMOTmyAnw==", - "requires": { - "gaxios": "^1.0.4", - "google-p12-pem": "^1.0.0", - "jws": "^3.1.5", - "mime": "^2.2.0", - "pify": "^4.0.0" - } - }, - "https-proxy-agent": { - "version": "2.2.4", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-2.2.4.tgz", - "integrity": "sha512-OmvfoQ53WLjtA9HeYP9RNrWMJzzAz1JGaSFr1nijg0PVR1JaD/xbJq1mdEIIlxGpXp9eSe/O2LgU9DJmTPd0Eg==", - "requires": { - "agent-base": "^4.3.0", - "debug": "^3.1.0" - } - }, - "json-bigint": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/json-bigint/-/json-bigint-0.3.1.tgz", - "integrity": "sha512-DGWnSzmusIreWlEupsUelHrhwmPPE+FiQvg+drKfk2p+bdEYa5mp4PJ8JsCWqae0M2jQNb0HPvnwvf1qOTThzQ==", - "requires": { - "bignumber.js": "^9.0.0" - } - }, - "lru-cache": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", - "integrity": "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==", - "requires": { - "yallist": "^3.0.2" - } - }, - "mime": { - "version": "2.4.6", - "resolved": "https://registry.npmjs.org/mime/-/mime-2.4.6.tgz", - "integrity": "sha512-RZKhC3EmpBchfTGBVb8fb+RL2cWyw/32lshnsETttkBAyAUXSGHxbEJWWRXc751DrIxG1q04b8QwMbAwkRPpUA==" - }, - "node-forge": { - "version": "0.8.5", - "resolved": "https://registry.npmjs.org/node-forge/-/node-forge-0.8.5.tgz", - "integrity": "sha512-vFMQIWt+J/7FLNyKouZ9TazT74PRV3wgv9UT4cRjC8BffxFbKXkgIWR42URCPSnHm/QDz6BOlb2Q0U4+VQT67Q==" - } - } - }, - "googleapis-common": { - "version": "0.7.2", - "resolved": "https://registry.npmjs.org/googleapis-common/-/googleapis-common-0.7.2.tgz", - "integrity": "sha512-9DEJIiO4nS7nw0VE1YVkEfXEj8x8MxsuB+yZIpOBULFSN9OIKcUU8UuKgSZFU4lJmRioMfngktrbkMwWJcUhQg==", - "requires": { - "gaxios": "^1.2.2", - "google-auth-library": "^3.0.0", - "pify": "^4.0.0", - "qs": "^6.5.2", - "url-template": "^2.0.8", - "uuid": "^3.2.1" - }, - "dependencies": { - "agent-base": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-4.3.0.tgz", - "integrity": "sha512-salcGninV0nPrwpGNn4VTXBb1SOuXQBiqbrNXoeizJsHrsL6ERFM2Ne3JUSBWRE6aeNJI2ROP/WEEIDUiDe3cg==", - "requires": { - "es6-promisify": "^5.0.0" - } - }, - "gaxios": { - "version": "1.8.4", - "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-1.8.4.tgz", - "integrity": "sha512-BoENMnu1Gav18HcpV9IleMPZ9exM+AvUjrAOV4Mzs/vfz2Lu/ABv451iEXByKiMPn2M140uul1txXCg83sAENw==", - "requires": { - "abort-controller": "^3.0.0", - "extend": "^3.0.2", - "https-proxy-agent": "^2.2.1", - "node-fetch": "^2.3.0" - } - }, - "gcp-metadata": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/gcp-metadata/-/gcp-metadata-1.0.0.tgz", - "integrity": "sha512-Q6HrgfrCQeEircnNP3rCcEgiDv7eF9+1B+1MMgpE190+/+0mjQR8PxeOaRgxZWmdDAF9EIryHB9g1moPiw1SbQ==", - "requires": { - "gaxios": "^1.0.2", - "json-bigint": "^0.3.0" - } - }, - "google-auth-library": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-3.1.2.tgz", - "integrity": "sha512-cDQMzTotwyWMrg5jRO7q0A4TL/3GWBgO7I7q5xGKNiiFf9SmGY/OJ1YsLMgI2MVHHsEGyrqYnbnmV1AE+Z6DnQ==", - "requires": { - "base64-js": "^1.3.0", - "fast-text-encoding": "^1.0.0", - "gaxios": "^1.2.1", - "gcp-metadata": "^1.0.0", - "gtoken": "^2.3.2", - "https-proxy-agent": "^2.2.1", - "jws": "^3.1.5", - "lru-cache": "^5.0.0", - "semver": "^5.5.0" - } - }, - "google-p12-pem": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/google-p12-pem/-/google-p12-pem-1.0.4.tgz", - "integrity": "sha512-SwLAUJqUfTB2iS+wFfSS/G9p7bt4eWcc2LyfvmUXe7cWp6p3mpxDo6LLI29MXdU6wvPcQ/up298X7GMC5ylAlA==", - "requires": { - "node-forge": "^0.8.0", - "pify": "^4.0.0" - } - }, - "gtoken": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-2.3.3.tgz", - "integrity": "sha512-EaB49bu/TCoNeQjhCYKI/CurooBKkGxIqFHsWABW0b25fobBYVTMe84A8EBVVZhl8emiUdNypil9huMOTmyAnw==", - "requires": { - "gaxios": "^1.0.4", - "google-p12-pem": "^1.0.0", - "jws": "^3.1.5", - "mime": "^2.2.0", - "pify": "^4.0.0" - } - }, - "https-proxy-agent": { - "version": "2.2.4", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-2.2.4.tgz", - "integrity": "sha512-OmvfoQ53WLjtA9HeYP9RNrWMJzzAz1JGaSFr1nijg0PVR1JaD/xbJq1mdEIIlxGpXp9eSe/O2LgU9DJmTPd0Eg==", - "requires": { - "agent-base": "^4.3.0", - "debug": "^3.1.0" - } - }, - "json-bigint": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/json-bigint/-/json-bigint-0.3.1.tgz", - "integrity": "sha512-DGWnSzmusIreWlEupsUelHrhwmPPE+FiQvg+drKfk2p+bdEYa5mp4PJ8JsCWqae0M2jQNb0HPvnwvf1qOTThzQ==", - "requires": { - "bignumber.js": "^9.0.0" - } - }, - "lru-cache": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", - "integrity": "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==", - "requires": { - "yallist": "^3.0.2" - } - }, - "mime": { - "version": "2.4.6", - "resolved": "https://registry.npmjs.org/mime/-/mime-2.4.6.tgz", - "integrity": "sha512-RZKhC3EmpBchfTGBVb8fb+RL2cWyw/32lshnsETttkBAyAUXSGHxbEJWWRXc751DrIxG1q04b8QwMbAwkRPpUA==" - }, - "node-forge": { - "version": "0.8.5", - "resolved": "https://registry.npmjs.org/node-forge/-/node-forge-0.8.5.tgz", - "integrity": "sha512-vFMQIWt+J/7FLNyKouZ9TazT74PRV3wgv9UT4cRjC8BffxFbKXkgIWR42URCPSnHm/QDz6BOlb2Q0U4+VQT67Q==" - }, - "uuid": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", - "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==" - } - } - }, "gtoken": { "version": "5.0.5", "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-5.0.5.tgz", @@ -813,11 +438,6 @@ } } }, - "has-unicode": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz", - "integrity": "sha1-4Ob+aijPUROIVeCG0Wkedx3iqLk=" - }, "http-errors": { "version": "1.7.2", "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.7.2.tgz", @@ -864,61 +484,26 @@ "safer-buffer": ">= 2.1.2 < 3" } }, - "ignore-walk": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/ignore-walk/-/ignore-walk-3.0.3.tgz", - "integrity": "sha512-m7o6xuOaT1aqheYHKf8W6J5pYH85ZI9w077erOzLje3JsB1gkafkAhHHY19dqjulgIZHFm32Cp5uNZgcQqdJKw==", - "requires": { - "minimatch": "^3.0.4" - } - }, "inflection": { "version": "1.12.0", "resolved": "https://registry.npmjs.org/inflection/-/inflection-1.12.0.tgz", "integrity": "sha1-ogCTVlbW9fa8TcdQLhrstwMihBY=" }, - "inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", - "requires": { - "once": "^1.3.0", - "wrappy": "1" - } - }, "inherits": { "version": "2.0.4", "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==" }, - "ini": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.5.tgz", - "integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==" - }, "ipaddr.js": { "version": "1.9.1", "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==" }, - "is-fullwidth-code-point": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", - "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", - "requires": { - "number-is-nan": "^1.0.0" - } - }, "is-stream": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.0.tgz", "integrity": "sha512-XCoy+WlUr7d1+Z8GgSuXmpuUFC9fOhRXglJMx+dwLKTkL44Cjd4W1Z5P+BQZpr+cR93aGP4S/s7Ftw6Nd/kiEw==" }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" - }, "json-bigint": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/json-bigint/-/json-bigint-1.0.0.tgz", @@ -1051,44 +636,6 @@ "mime-db": "1.44.0" } }, - "minimatch": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", - "requires": { - "brace-expansion": "^1.1.7" - } - }, - "minimist": { - "version": "1.2.5", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", - "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==" - }, - "minipass": { - "version": "2.9.0", - "resolved": "https://registry.npmjs.org/minipass/-/minipass-2.9.0.tgz", - "integrity": "sha512-wxfUjg9WebH+CUDX/CdbRlh5SmfZiy/hpkxaRI16Y9W56Pa75sWgd/rvFilSgrauD9NyFymP/+JFV3KwzIsJeg==", - "requires": { - "safe-buffer": "^5.1.2", - "yallist": "^3.0.0" - } - }, - "minizlib": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/minizlib/-/minizlib-1.3.3.tgz", - "integrity": "sha512-6ZYMOEnmVsdCeTJVE0W9ZD+pVnE8h9Hma/iOwwRDsdQoePpoX56/8B6z3P9VNwppJuBKNRuFDRNRqRWexT9G9Q==", - "requires": { - "minipass": "^2.9.0" - } - }, - "mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "requires": { - "minimist": "^1.2.5" - } - }, "moment": { "version": "2.29.1", "resolved": "https://registry.npmjs.org/moment/-/moment-2.29.1.tgz", @@ -1107,26 +654,11 @@ "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" }, - "needle": { - "version": "2.5.2", - "resolved": "https://registry.npmjs.org/needle/-/needle-2.5.2.tgz", - "integrity": "sha512-LbRIwS9BfkPvNwNHlsA41Q29kL2L/6VaOJ0qisM5lLWsTV3nP15abO5ITL6L81zqFhzjRKDAYjpcBcwM0AVvLQ==", - "requires": { - "debug": "^3.2.6", - "iconv-lite": "^0.4.4", - "sax": "^1.2.4" - } - }, "negotiator": { "version": "0.6.2", "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.2.tgz", "integrity": "sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw==" }, - "node-addon-api": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-3.0.2.tgz", - "integrity": "sha512-+D4s2HCnxPd5PjjI0STKwncjXTUKKqm74MDMz9OPXavjsGmjkvwgLtA5yoxJUdmpj52+2u+RrXgPipahKczMKg==" - }, "node-fetch": { "version": "2.6.1", "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.1.tgz", @@ -1137,71 +669,6 @@ "resolved": "https://registry.npmjs.org/node-forge/-/node-forge-0.10.0.tgz", "integrity": "sha512-PPmu8eEeG9saEUvI97fm4OYxXVB6bFvyNTyiUOBichBpFG8A1Ljw3bY62+5oOjDEMHRnd0Y7HQ+x7uzxOzC6JA==" }, - "node-pre-gyp": { - "version": "0.15.0", - "resolved": "https://registry.npmjs.org/node-pre-gyp/-/node-pre-gyp-0.15.0.tgz", - "integrity": "sha512-7QcZa8/fpaU/BKenjcaeFF9hLz2+7S9AqyXFhlH/rilsQ/hPZKK32RtR5EQHJElgu+q5RfbJ34KriI79UWaorA==", - "requires": { - "detect-libc": "^1.0.2", - "mkdirp": "^0.5.3", - "needle": "^2.5.0", - "nopt": "^4.0.1", - "npm-packlist": "^1.1.6", - "npmlog": "^4.0.2", - "rc": "^1.2.7", - "rimraf": "^2.6.1", - "semver": "^5.3.0", - "tar": "^4.4.2" - } - }, - "nopt": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-4.0.3.tgz", - "integrity": "sha512-CvaGwVMztSMJLOeXPrez7fyfObdZqNUK1cPAEzLHrTybIua9pMdmmPR5YwtfNftIOMv3DPUhFaxsZMNTQO20Kg==", - "requires": { - "abbrev": "1", - "osenv": "^0.1.4" - } - }, - "npm-bundled": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/npm-bundled/-/npm-bundled-1.1.1.tgz", - "integrity": "sha512-gqkfgGePhTpAEgUsGEgcq1rqPXA+tv/aVBlgEzfXwA1yiUJF7xtEt3CtVwOjNYQOVknDk0F20w58Fnm3EtG0fA==", - "requires": { - "npm-normalize-package-bin": "^1.0.1" - } - }, - "npm-normalize-package-bin": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-1.0.1.tgz", - "integrity": "sha512-EPfafl6JL5/rU+ot6P3gRSCpPDW5VmIzX959Ob1+ySFUuuYHWHekXpwdUZcKP5C+DS4GEtdJluwBjnsNDl+fSA==" - }, - "npm-packlist": { - "version": "1.4.8", - "resolved": "https://registry.npmjs.org/npm-packlist/-/npm-packlist-1.4.8.tgz", - "integrity": "sha512-5+AZgwru5IevF5ZdnFglB5wNlHG1AOOuw28WhUq8/8emhBmLv6jX5by4WJCh7lW0uSYZYS6DXqIsyZVIXRZU9A==", - "requires": { - "ignore-walk": "^3.0.1", - "npm-bundled": "^1.0.1", - "npm-normalize-package-bin": "^1.0.1" - } - }, - "npmlog": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-4.1.2.tgz", - "integrity": "sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg==", - "requires": { - "are-we-there-yet": "~1.1.2", - "console-control-strings": "~1.1.0", - "gauge": "~2.7.3", - "set-blocking": "~2.0.0" - } - }, - "number-is-nan": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", - "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=" - }, "object-assign": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", @@ -1215,33 +682,6 @@ "ee-first": "1.1.1" } }, - "once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", - "requires": { - "wrappy": "1" - } - }, - "os-homedir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", - "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=" - }, - "os-tmpdir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", - "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=" - }, - "osenv": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/osenv/-/osenv-0.1.5.tgz", - "integrity": "sha512-0CWcCECdMVc2Rw3U5w9ZjqX6ga6ubk1xDVKxtBQPK7wis/0F2r9T6k4ydGYhecl7YUBxBVxhL5oisPsNxAPe2g==", - "requires": { - "os-homedir": "^1.0.0", - "os-tmpdir": "^1.0.0" - } - }, "packet-reader": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/packet-reader/-/packet-reader-1.0.0.tgz", @@ -1252,11 +692,6 @@ "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==" }, - "path-is-absolute": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" - }, "path-to-regexp": { "version": "0.1.7", "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", @@ -1316,11 +751,6 @@ "split2": "^3.1.1" } }, - "pify": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/pify/-/pify-4.0.1.tgz", - "integrity": "sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g==" - }, "postgres-array": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/postgres-array/-/postgres-array-2.0.0.tgz", @@ -1344,11 +774,6 @@ "xtend": "^4.0.0" } }, - "process-nextick-args": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", - "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==" - }, "proxy-addr": { "version": "2.0.6", "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.6.tgz", @@ -1379,31 +804,6 @@ "unpipe": "1.0.0" } }, - "rc": { - "version": "1.2.8", - "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", - "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", - "requires": { - "deep-extend": "^0.6.0", - "ini": "~1.3.0", - "minimist": "^1.2.0", - "strip-json-comments": "~2.0.1" - } - }, - "readable-stream": { - "version": "2.3.7", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.7.tgz", - "integrity": "sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==", - "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" - } - }, "retry-as-promised": { "version": "3.2.0", "resolved": "https://registry.npmjs.org/retry-as-promised/-/retry-as-promised-3.2.0.tgz", @@ -1412,14 +812,6 @@ "any-promise": "^1.3.0" } }, - "rimraf": { - "version": "2.7.1", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.7.1.tgz", - "integrity": "sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w==", - "requires": { - "glob": "^7.1.3" - } - }, "safe-buffer": { "version": "5.1.2", "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", @@ -1430,11 +822,6 @@ "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" }, - "sax": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/sax/-/sax-1.2.4.tgz", - "integrity": "sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw==" - }, "semver": { "version": "5.7.1", "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", @@ -1533,21 +920,11 @@ "send": "0.17.1" } }, - "set-blocking": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", - "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=" - }, "setprototypeof": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.1.tgz", "integrity": "sha512-JvdAWfbXeIGaZ9cILp38HntZSFSo3mWg6xGcJJsd+d4aRMOqauag1C63dJfDw7OaMYwEbHMOxEZ1lqVRYP2OAw==" }, - "signal-exit": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.3.tgz", - "integrity": "sha512-VUJ49FC8U1OxwZLxIbTTrDvLnf/6TDgxZcK8wxR8zs13xpx7xbG60ndBlhNrFi2EMuFRoeDoJO7wthSLq42EjA==" - }, "split2": { "version": "3.2.2", "resolved": "https://registry.npmjs.org/split2/-/split2-3.2.2.tgz", @@ -1573,16 +950,6 @@ "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", "integrity": "sha1-Fhx9rBd2Wf2YEfQ3cfqZOBR4Yow=" }, - "string-width": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", - "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", - "requires": { - "code-point-at": "^1.0.0", - "is-fullwidth-code-point": "^1.0.0", - "strip-ansi": "^3.0.0" - } - }, "string_decoder": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", @@ -1591,33 +958,6 @@ "safe-buffer": "~5.1.0" } }, - "strip-ansi": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "requires": { - "ansi-regex": "^2.0.0" - } - }, - "strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=" - }, - "tar": { - "version": "4.4.13", - "resolved": "https://registry.npmjs.org/tar/-/tar-4.4.13.tgz", - "integrity": "sha512-w2VwSrBoHa5BsSyH+KxEqeQBAllHhccyMFVHtGtdMpF4W7IRWfZjFiQceJPChOeTsSDVUpER2T8FA93pr0L+QA==", - "requires": { - "chownr": "^1.1.1", - "fs-minipass": "^1.2.5", - "minipass": "^2.8.6", - "minizlib": "^1.2.1", - "mkdirp": "^0.5.0", - "safe-buffer": "^5.1.2", - "yallist": "^3.0.3" - } - }, "toidentifier": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.0.tgz", @@ -1642,11 +982,6 @@ "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=" }, - "url-template": { - "version": "2.0.8", - "resolved": "https://registry.npmjs.org/url-template/-/url-template-2.0.8.tgz", - "integrity": "sha1-/FZaPMy/93MMd19WQflVV5FDnyE=" - }, "util-deprecate": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", @@ -1672,14 +1007,6 @@ "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", "integrity": "sha1-IpnwLG3tMNSllhsLn3RSShj2NPw=" }, - "wide-align": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/wide-align/-/wide-align-1.1.3.tgz", - "integrity": "sha512-QGkOQc8XL6Bt5PwnsExKBPuMKBxnGxWWW3fU55Xt4feHozMUhdUMaBCk290qpm/wG5u/RSKzwdAC4i51YigihA==", - "requires": { - "string-width": "^1.0.2 || 2" - } - }, "wkx": { "version": "0.5.0", "resolved": "https://registry.npmjs.org/wkx/-/wkx-0.5.0.tgz", @@ -1688,20 +1015,10 @@ "@types/node": "*" } }, - "wrappy": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" - }, "xtend": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==" - }, - "yallist": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.1.1.tgz", - "integrity": "sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==" } } } diff --git a/server/package.json b/server/package.json index 379bf23..3677c9d 100644 --- a/server/package.json +++ b/server/package.json @@ -5,18 +5,18 @@ "main": "index.js", "scripts": { "test": "echo \"Error: no test specified\" && exit 1", - "dev": "nodemon app.js" + "dev": "nodemon app.js", + "start": "node app.js" }, "keywords": [], "author": "torianyap", "license": "ISC", "dependencies": { "axios": "^0.21.0", - "bcrypt": "^5.0.0", + "bcryptjs": "^2.4.3", "cors": "^2.8.5", "express": "^4.17.1", "google-auth-library": "^6.1.3", - "googleapis": "^39.2.0", "jsonwebtoken": "^8.5.1", "pg": "^8.4.2", "sequelize": "^6.3.5" From 846c05afa5c77706a0c5050de9db0642ab326556 Mon Sep 17 00:00:00 2001 From: torianyap Date: Mon, 2 Nov 2020 15:43:54 +0700 Subject: [PATCH 19/22] deploy heroku --- server/app.js | 1 + 1 file changed, 1 insertion(+) diff --git a/server/app.js b/server/app.js index 147ee06..8aa1a5e 100644 --- a/server/app.js +++ b/server/app.js @@ -2,6 +2,7 @@ if (process.env.NODE_ENV !== 'production') { require('dotenv').config() } + const express = require('express') const cors = require('cors') const router = require('./routes') From d1fc0aa87ff94d3f2068e3c020e45b2a49421579 Mon Sep 17 00:00:00 2001 From: torianyap Date: Mon, 2 Nov 2020 16:01:56 +0700 Subject: [PATCH 20/22] rewrite config.json --- server/app.js | 1 - server/config/config.json | 3 ++- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/server/app.js b/server/app.js index 8aa1a5e..147ee06 100644 --- a/server/app.js +++ b/server/app.js @@ -2,7 +2,6 @@ if (process.env.NODE_ENV !== 'production') { require('dotenv').config() } - const express = require('express') const cors = require('cors') const router = require('./routes') diff --git a/server/config/config.json b/server/config/config.json index bebff9b..eedd1d5 100644 --- a/server/config/config.json +++ b/server/config/config.json @@ -14,6 +14,7 @@ "dialect": "mysql" }, "production": { - "use_env_variable": "postgres://ndbaersqegmwbq:52801c4ce7fe42ac0b5a6b21e5783c5cf9a49b89434604186305e97b28cd8d7c@ec2-3-208-224-152.compute-1.amazonaws.com:5432/d2pnr7ord1rot7" + "use_env_variable": "DATABASE_URL", + "dialect": "postgres" } } From ed36e32c5b0ed2aad36d6efb8f417f1ef51dc783 Mon Sep 17 00:00:00 2001 From: torianyap Date: Mon, 2 Nov 2020 17:06:48 +0700 Subject: [PATCH 21/22] deployed --- client/.firebaserc | 5 ++++ client/.gitignore | 66 ++++++++++++++++++++++++++++++++++++++++++++ client/debug.log | 1 - client/firebase.json | 16 +++++++++++ client/functions.js | 3 ++ client/index.js | 5 ++-- 6 files changed, 93 insertions(+), 3 deletions(-) create mode 100644 client/.firebaserc create mode 100644 client/.gitignore delete mode 100644 client/debug.log create mode 100644 client/firebase.json diff --git a/client/.firebaserc b/client/.firebaserc new file mode 100644 index 0000000..9e35220 --- /dev/null +++ b/client/.firebaserc @@ -0,0 +1,5 @@ +{ + "projects": { + "default": "fancy-to-do-5ee22" + } +} diff --git a/client/.gitignore b/client/.gitignore new file mode 100644 index 0000000..dbb58ff --- /dev/null +++ b/client/.gitignore @@ -0,0 +1,66 @@ +# Logs +logs +*.log +npm-debug.log* +yarn-debug.log* +yarn-error.log* +firebase-debug.log* +firebase-debug.*.log* + +# Firebase cache +.firebase/ + +# Firebase config + +# Uncomment this if you'd like others to create their own Firebase project. +# For a team working on the same Firebase project(s), it is recommended to leave +# it commented so all members can deploy to the same project(s) in .firebaserc. +# .firebaserc + +# Runtime data +pids +*.pid +*.seed +*.pid.lock + +# Directory for instrumented libs generated by jscoverage/JSCover +lib-cov + +# Coverage directory used by tools like istanbul +coverage + +# nyc test coverage +.nyc_output + +# Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files) +.grunt + +# Bower dependency directory (https://bower.io/) +bower_components + +# node-waf configuration +.lock-wscript + +# Compiled binary addons (http://nodejs.org/api/addons.html) +build/Release + +# Dependency directories +node_modules/ + +# Optional npm cache directory +.npm + +# Optional eslint cache +.eslintcache + +# Optional REPL history +.node_repl_history + +# Output of 'npm pack' +*.tgz + +# Yarn Integrity file +.yarn-integrity + +# dotenv environment variables file +.env diff --git a/client/debug.log b/client/debug.log deleted file mode 100644 index 98e90f8..0000000 --- a/client/debug.log +++ /dev/null @@ -1 +0,0 @@ -[1101/094326.183:ERROR:directory_reader_win.cc(43)] FindFirstFile: The system cannot find the path specified. (0x3) diff --git a/client/firebase.json b/client/firebase.json new file mode 100644 index 0000000..b3a5ba8 --- /dev/null +++ b/client/firebase.json @@ -0,0 +1,16 @@ +{ + "hosting": { + "public": ".", + "ignore": [ + "firebase.json", + "**/.*", + "**/node_modules/**" + ], + "rewrites": [ + { + "source": "**", + "destination": "/index.html" + } + ] + } +} diff --git a/client/functions.js b/client/functions.js index 95df811..58d282d 100644 --- a/client/functions.js +++ b/client/functions.js @@ -34,6 +34,9 @@ function source(description) { case "sunny": source = "https://www.flaticon.com/svg/static/icons/svg/2917/2917242.svg" break; + case "clear": + source = "https://www.flaticon.com/svg/static/icons/svg/2917/2917242.svg" + break; case "windy": source = "https://www.flaticon.com/svg/static/icons/svg/2917/2917242.svg" break; diff --git a/client/index.js b/client/index.js index 9cd44d6..d305ce3 100644 --- a/client/index.js +++ b/client/index.js @@ -1,4 +1,4 @@ -const SERVER = 'http://localhost:3000' +const SERVER = 'https://fancy-todo-tori.herokuapp.com' const Toast = Swal.mixin({ toast: true, @@ -113,6 +113,7 @@ const register = e => { }) }) .fail(err => { + console.log(err) Swal.fire({ icon: 'error', title: 'Error', @@ -165,7 +166,7 @@ const login = e => { function onSignIn(googleUser) { const profile = googleUser.getBasicProfile(); - const name = profile.gV + const name = profile.getName() const google_access_token = googleUser.getAuthResponse().id_token; $.ajax({ From 30365fae44a2832472e73faea0feeb6e68308c17 Mon Sep 17 00:00:00 2001 From: torianyap Date: Mon, 2 Nov 2020 17:09:06 +0700 Subject: [PATCH 22/22] add readme --- README.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/README.md b/README.md index 4f53bcf..6fb762e 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,8 @@ # FancyTodo +* Web:
+ https://fancy-to-do-5ee22.web.app/ +---- List of available endpoints: * POST /register * POST /login