@laboratoria/sdk-js 0.2.0 → 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,5 +1,7 @@
1
1
  ## Laboratoria JavaScript (browser) SDK
2
2
 
3
+ [![Node.js CI](https://github.com/Laboratoria/sdk-js/actions/workflows/node.js.yml/badge.svg)](https://github.com/Laboratoria/sdk-js/actions/workflows/node.js.yml)
4
+
3
5
  :warning: This tool is still in draft stage and is likely to change without
4
6
  notice.
5
7
 
@@ -25,7 +27,6 @@ const app = createApp({
25
27
  firebaseApiKey: '',
26
28
  firebaseProject: '',
27
29
  coreApiUrl: '',
28
- teamApiUrl: '',
29
30
  jobsApiUrl: '',
30
31
  });
31
32
  ```
@@ -79,7 +80,6 @@ app.user.create({
79
80
  ### Cohorts
80
81
 
81
82
  ```js
82
- // Cohorts API
83
83
  app.cohort.findMany({
84
84
  where: {
85
85
  end: { gt: new Date() },
@@ -96,13 +96,50 @@ app.cohort.findMany({
96
96
 
97
97
  ### Students
98
98
 
99
+ WIP
100
+
99
101
  ### Dropouts
100
102
 
103
+ WIP
101
104
 
102
105
  ### Projects
103
106
 
104
107
  ```js
105
108
  app.project.findMany();
106
109
 
107
- // app.learningObjectives.
110
+ app.project.findMany({ tag: 'v3.0.0' });
111
+
112
+ app.project.findMany({
113
+ locale: 'es-ES',
114
+ track: 'js',
115
+ });
116
+
117
+ app.project.findById('cipher');
118
+
119
+ app.project.findById('cipher', { tag: 'v3.0.0' });
108
120
  ```
121
+
122
+ ### Topics
123
+
124
+ ```js
125
+ app.topic.findMany();
126
+
127
+ app.topic.findMany({ tag: 'v3.0.0' });
128
+
129
+ app.topic.findMany({
130
+ locale: 'es-ES',
131
+ track: 'js',
132
+ });
133
+
134
+ app.topic.findById('javascript');
135
+
136
+ app.topic.findById('javascript', { tag: 'v3.0.0' });
137
+ ```
138
+
139
+ ### Learning Objectives
140
+
141
+ ```js
142
+ app.learningObjective.findMany();
143
+
144
+ app.learningObjective.findMany({ tag: 'v3.0.0' });
145
+ ```
package/index.js CHANGED
@@ -6,14 +6,13 @@ import {
6
6
  signOut,
7
7
  } from 'firebase/auth';
8
8
  import { createAPI as createCoreAPI } from './lib/core';
9
+ import { createAPI as createCurriculumAPI } from './lib/curriculum';
9
10
  import { createAPI as createJobsAPI } from './lib/jobs';
10
- import { createAPI as createTeamAPI } from './lib/team';
11
11
 
12
12
  export const createApp = ({
13
13
  firebaseApiKey = 'AIzaSyAXbaEbpq8NOfn0r8mIrcoHvoGRkJThwdc',
14
14
  firebaseProject = 'laboratoria-la',
15
15
  coreApiUrl = 'https://us-central1-outpost-272720.cloudfunctions.net/core-api',
16
- teamApiUrl = 'https://us-central1-outpost-272720.cloudfunctions.net/team-api',
17
16
  jobsApiUrl = 'https://us-central1-outpost-272720.cloudfunctions.net/jobs-api',
18
17
  } = {}) => {
19
18
  const firebaseApp = initializeApp({
@@ -26,8 +25,8 @@ export const createApp = ({
26
25
  const firebaseAuth = getAuth(firebaseApp);
27
26
  const state = { authUser: undefined, user: undefined };
28
27
  const coreAPI = createCoreAPI(coreApiUrl, state);
29
- const teamAPI = createTeamAPI(teamApiUrl, state);
30
28
  const jobsAPI = createJobsAPI(jobsApiUrl, state);
29
+ const curriculumAPI = createCurriculumAPI();
31
30
 
32
31
  const authAPI = {
33
32
  onChange: fn => onAuthStateChanged(firebaseAuth, (authUser) => {
@@ -56,9 +55,9 @@ export const createApp = ({
56
55
  };
57
56
 
58
57
  return {
59
- auth: authAPI,
60
58
  ...jobsAPI,
61
- ...teamAPI,
59
+ ...curriculumAPI,
62
60
  ...coreAPI,
61
+ auth: authAPI,
63
62
  };
64
63
  };
package/index.spec.js CHANGED
@@ -5,10 +5,16 @@ import {
5
5
  signInWithEmailAndPassword,
6
6
  signOut,
7
7
  } from 'firebase/auth';
8
- import { createClient } from './lib/client.js';
8
+ import { createAPI as createCoreAPI } from './lib/core';
9
9
  import { createApp } from './index.js';
10
10
 
11
- jest.mock('./lib/client.js');
11
+ jest.mock('./lib/core.js', () => ({
12
+ createAPI: jest.fn().mockReturnValue({
13
+ user: {
14
+ findById: jest.fn().mockResolvedValue({}),
15
+ },
16
+ }),
17
+ }));
12
18
 
13
19
  beforeEach(() => {
14
20
  initializeApp.mockClear();
@@ -40,7 +46,7 @@ describe('app.auth.onChange', () => {
40
46
  });
41
47
  });
42
48
 
43
- it('should fetch user from db when authenticated and add isStaff, isManager, etc', (done) => {
49
+ it('should fetch user from db when authenticated using coreAPI', (done) => {
44
50
  const { auth } = createApp();
45
51
  const mockAuthUser = { uid: 'xxx', getIdToken: () => 'token' };
46
52
  const userMock = { uid: 'xxx', email: 'foo@bar.baz' };
@@ -50,17 +56,11 @@ describe('app.auth.onChange', () => {
50
56
  return () => { };
51
57
  });
52
58
 
53
- createClient().mockResolvedValueOnce(userMock);
59
+ createCoreAPI().user.findById.mockResolvedValue(userMock);
54
60
 
55
61
  auth.onChange(({ authUser, user }) => {
56
62
  expect(authUser).toEqual(mockAuthUser);
57
- expect(user).toEqual({
58
- ...userMock,
59
- isStaff: false,
60
- isManager: false,
61
- isFinance: false,
62
- isAdmin: false,
63
- });
63
+ expect(user).toEqual(userMock);
64
64
  done();
65
65
  });
66
66
  });
@@ -76,7 +76,7 @@ describe('app.auth.onChange', () => {
76
76
  return () => { };
77
77
  });
78
78
 
79
- createClient().mockRejectedValueOnce(error);
79
+ createCoreAPI().user.findById.mockRejectedValueOnce(error);
80
80
 
81
81
  auth.onChange(({ authUser, user }) => {
82
82
  expect(authUser).toBeNull();
package/lib/core.js CHANGED
@@ -1,8 +1,13 @@
1
1
  import md5 from 'blueimp-md5';
2
+ import currencies from './currencies';
3
+ import roles from './roles';
2
4
  import { createModels, extendSchemaDefinitions } from './model';
3
5
  import schema from '../schemas/core.json';
4
6
 
5
7
  const extended = {
8
+ Country: {
9
+ plural: 'countries',
10
+ },
6
11
  User: {
7
12
  primaryKey: 'uid',
8
13
  inputProps: [
@@ -69,6 +74,7 @@ const extended = {
69
74
  properties: {},
70
75
  parse: (props) => {
71
76
  const now = Date.now();
77
+ // TODO: Handle case where start and/or end have not been selected in query
72
78
  const status = (
73
79
  props.start > now
74
80
  ? 'upcoming'
@@ -113,6 +119,43 @@ const extended = {
113
119
  'cohort.name',
114
120
  ],
115
121
  },
122
+ Contract: {
123
+ inputProps: [
124
+ 'user',
125
+ 'countryCode',
126
+ 'currency',
127
+ 'isEmployment',
128
+ 'feeBasis',
129
+ 'feeAmount',
130
+ 'hoursPerWeek',
131
+ 'start',
132
+ 'end',
133
+ ],
134
+ properties: {
135
+ countryCode: {
136
+ enum: ['BR', 'CL', 'CO', 'MX', 'PE'],
137
+ },
138
+ currency: {
139
+ enum: currencies,
140
+ },
141
+ },
142
+ },
143
+ Gig: {
144
+ inputProps: [
145
+ // 'contract',
146
+ 'cohort',
147
+ 'user',
148
+ 'role',
149
+ 'hoursPerWeek',
150
+ 'start',
151
+ 'end',
152
+ ],
153
+ properties: {
154
+ role: {
155
+ enum: roles,
156
+ },
157
+ },
158
+ },
116
159
  };
117
160
 
118
161
  export const createAPI = (url, state) => createModels(url, state, {
@@ -0,0 +1,59 @@
1
+ const releasesUrl = 'https://api.github.com/repos/Laboratoria/bootcamp/releases';
2
+ const rawUrl = 'https://raw.githubusercontent.com/Laboratoria/bootcamp';
3
+
4
+ const getLatestVersion = () => fetch(`${releasesUrl}/latest`)
5
+ .then(resp => resp.json())
6
+ .then(({ tag_name }) => tag_name);
7
+
8
+ const fetchProjects = async tag => (
9
+ fetch(`${rawUrl}/${tag || await getLatestVersion()}/dist/projects.json`)
10
+ .then(resp => resp.json())
11
+ );
12
+
13
+ const fetchProject = async (slug, tag) => (
14
+ fetch(`${rawUrl}/${tag || await getLatestVersion()}/dist/projects/${slug}.json`)
15
+ .then(resp => resp.json())
16
+ );
17
+
18
+ const fetchTopics = async tag => (
19
+ fetch(`${rawUrl}/${tag || await getLatestVersion()}/dist/topics.json`)
20
+ .then(resp => resp.json())
21
+ );
22
+
23
+ const fetchTopic = async (slug, tag) => (
24
+ fetch(`${rawUrl}/${tag || await getLatestVersion()}/dist/topics/${slug}.json`)
25
+ .then(resp => resp.json())
26
+ );
27
+
28
+ const fetchLearningObjectives = async tag => (
29
+ fetch(`${rawUrl}/${tag || await getLatestVersion()}/dist/learning-objectives.json`)
30
+ .then(resp => resp.json())
31
+ );
32
+
33
+ const filterByLocaleAndTrack = opts => arr => arr.filter((obj) => {
34
+ if (opts.locale && opts.locale !== obj.locale) {
35
+ return false;
36
+ }
37
+ if (opts.track && opts.track !== obj.track) {
38
+ return false;
39
+ }
40
+ return true;
41
+ });
42
+
43
+ export const createAPI = () => {
44
+ return {
45
+ projects: {
46
+ findMany: (opts = {}) => fetchProjects(opts.tag)
47
+ .then(filterByLocaleAndTrack(opts)),
48
+ findById: (slug, opts = {}) => fetchProject(slug, opts.tag),
49
+ },
50
+ topics: {
51
+ findMany: (opts = {}) => fetchTopics(opts.tag)
52
+ .then(filterByLocaleAndTrack(opts)),
53
+ findById: (slug, opts = {}) => fetchTopic(slug, opts.tag),
54
+ },
55
+ learningObjectives: {
56
+ findMany: (opts = {}) => fetchLearningObjectives(opts.tag),
57
+ },
58
+ };
59
+ };
@@ -0,0 +1,194 @@
1
+ import { createAPI } from './curriculum';
2
+
3
+ describe('projects', () => {
4
+ describe('findMany', () => {
5
+ // TODO: errores HTTP, GitHub caido, repo borrado, etc...
6
+
7
+ it('sends request to get latest version and then corresponding json', () => {
8
+ global.fetch = jest.fn().mockImplementation(async url => ({
9
+ status: 200,
10
+ json: jest.fn().mockResolvedValue(
11
+ url.startsWith('https://api.')
12
+ ? { tag_name: 'v4.0.0' }
13
+ : []
14
+ ),
15
+ }));
16
+
17
+ return createAPI().projects.findMany()
18
+ .then((projects) => {
19
+ expect(projects).toEqual([]);
20
+ expect(global.fetch).toHaveBeenCalledTimes(2);
21
+ expect(global.fetch).toHaveBeenNthCalledWith(
22
+ 1,
23
+ 'https://api.github.com/repos/Laboratoria/bootcamp/releases/latest',
24
+ );
25
+ expect(global.fetch).toHaveBeenNthCalledWith(
26
+ 2,
27
+ 'https://raw.githubusercontent.com/Laboratoria/bootcamp/v4.0.0/dist/projects.json',
28
+ );
29
+ });
30
+ });
31
+
32
+ it('gets projects in specific tag when passed as option', () => {
33
+ global.fetch = jest.fn().mockImplementation(async url => ({
34
+ status: 200,
35
+ json: jest.fn().mockResolvedValue(
36
+ url.startsWith('https://api.')
37
+ ? { tag_name: 'v4.0.0' }
38
+ : []
39
+ ),
40
+ }));
41
+
42
+ return createAPI().projects.findMany({ tag: 'v3.0.0' })
43
+ .then((projects) => {
44
+ expect(projects).toEqual([]);
45
+ expect(global.fetch).toHaveBeenCalledTimes(1);
46
+ expect(global.fetch).toHaveBeenCalledWith(
47
+ 'https://raw.githubusercontent.com/Laboratoria/bootcamp/v3.0.0/dist/projects.json',
48
+ );
49
+ });
50
+ });
51
+
52
+ it('gets projects in specific tag when passed as option', () => {
53
+ global.fetch = jest.fn().mockImplementation(async url => ({
54
+ status: 200,
55
+ json: jest.fn().mockResolvedValue(
56
+ url.startsWith('https://api.')
57
+ ? { tag_name: 'v4.0.0' }
58
+ : [
59
+ { locale: 'es-ES', track: 'ux' },
60
+ { locale: 'es-ES', track: 'js' },
61
+ { locale: 'pt-BR', track: 'ux' },
62
+ ]
63
+ ),
64
+ }));
65
+
66
+ return createAPI().projects.findMany({
67
+ tag: 'v3.0.0',
68
+ locale: 'es-ES',
69
+ track: 'ux',
70
+ })
71
+ .then((projects) => {
72
+ expect(projects).toEqual([{ locale: 'es-ES', track: 'ux' }]);
73
+ expect(global.fetch).toHaveBeenCalledTimes(1);
74
+ expect(global.fetch).toHaveBeenCalledWith(
75
+ 'https://raw.githubusercontent.com/Laboratoria/bootcamp/v3.0.0/dist/projects.json',
76
+ );
77
+ });
78
+ });
79
+
80
+ // it should filter by tag, locale and track...
81
+ });
82
+
83
+ describe('findById', () => {
84
+ it('sends request to get latest version and then corresponding json', () => {
85
+ global.fetch = jest.fn().mockImplementation(async url => ({
86
+ status: 200,
87
+ json: jest.fn().mockResolvedValue(
88
+ url.startsWith('https://api.')
89
+ ? { tag_name: 'v4.0.0' }
90
+ : {}
91
+ ),
92
+ }));
93
+
94
+ return createAPI().projects.findById('cipher')
95
+ .then((project) => {
96
+ expect(project).toEqual({});
97
+ expect(global.fetch).toHaveBeenCalledTimes(2);
98
+ expect(global.fetch).toHaveBeenNthCalledWith(
99
+ 1,
100
+ 'https://api.github.com/repos/Laboratoria/bootcamp/releases/latest',
101
+ );
102
+ expect(global.fetch).toHaveBeenNthCalledWith(
103
+ 2,
104
+ 'https://raw.githubusercontent.com/Laboratoria/bootcamp/v4.0.0/dist/projects/cipher.json',
105
+ );
106
+ });
107
+ });
108
+ });
109
+ });
110
+
111
+ describe('topics', () => {
112
+ describe('findMany', () => {
113
+ it('sends request to get latest version and then corresponding json', () => {
114
+ global.fetch = jest.fn().mockImplementation(async url => ({
115
+ status: 200,
116
+ json: jest.fn().mockResolvedValue(
117
+ url.startsWith('https://api.')
118
+ ? { tag_name: 'v4.0.0' }
119
+ : []
120
+ ),
121
+ }));
122
+
123
+ return createAPI().topics.findMany()
124
+ .then((topics) => {
125
+ expect(topics).toEqual([]);
126
+ expect(global.fetch).toHaveBeenCalledTimes(2);
127
+ expect(global.fetch).toHaveBeenNthCalledWith(
128
+ 1,
129
+ 'https://api.github.com/repos/Laboratoria/bootcamp/releases/latest',
130
+ );
131
+ expect(global.fetch).toHaveBeenNthCalledWith(
132
+ 2,
133
+ 'https://raw.githubusercontent.com/Laboratoria/bootcamp/v4.0.0/dist/topics.json',
134
+ );
135
+ });
136
+ });
137
+ });
138
+
139
+ describe('findById', () => {
140
+ it('sends request to get latest version and then corresponding json', () => {
141
+ global.fetch = jest.fn().mockImplementation(async url => ({
142
+ status: 200,
143
+ json: jest.fn().mockResolvedValue(
144
+ url.startsWith('https://api.')
145
+ ? { tag_name: 'v4.0.0' }
146
+ : {}
147
+ ),
148
+ }));
149
+
150
+ return createAPI().topics.findById('javascript')
151
+ .then((topic) => {
152
+ expect(topic).toEqual({});
153
+ expect(global.fetch).toHaveBeenCalledTimes(2);
154
+ expect(global.fetch).toHaveBeenNthCalledWith(
155
+ 1,
156
+ 'https://api.github.com/repos/Laboratoria/bootcamp/releases/latest',
157
+ );
158
+ expect(global.fetch).toHaveBeenNthCalledWith(
159
+ 2,
160
+ 'https://raw.githubusercontent.com/Laboratoria/bootcamp/v4.0.0/dist/topics/javascript.json',
161
+ );
162
+ });
163
+ });
164
+ });
165
+ });
166
+
167
+ describe('learningObjectives', () => {
168
+ describe('findMany', () => {
169
+ it('sends request to get latest version and then corresponding json', () => {
170
+ global.fetch = jest.fn().mockImplementation(async url => ({
171
+ status: 200,
172
+ json: jest.fn().mockResolvedValue(
173
+ url.startsWith('https://api.')
174
+ ? { tag_name: 'v4.0.0' }
175
+ : []
176
+ ),
177
+ }));
178
+
179
+ return createAPI().learningObjectives.findMany()
180
+ .then((learningObjectives) => {
181
+ expect(learningObjectives).toEqual([]);
182
+ expect(global.fetch).toHaveBeenCalledTimes(2);
183
+ expect(global.fetch).toHaveBeenNthCalledWith(
184
+ 1,
185
+ 'https://api.github.com/repos/Laboratoria/bootcamp/releases/latest',
186
+ );
187
+ expect(global.fetch).toHaveBeenNthCalledWith(
188
+ 2,
189
+ 'https://raw.githubusercontent.com/Laboratoria/bootcamp/v4.0.0/dist/learning-objectives.json',
190
+ );
191
+ });
192
+ });
193
+ });
194
+ });
package/lib/model.js CHANGED
@@ -71,28 +71,6 @@ const createBuildURL = collectionName => (id, q) => {
71
71
  };
72
72
 
73
73
 
74
- const createBuildQuery = defaultInclude => (q = {}) => ({
75
- ...(!q.select && Object.keys(defaultInclude).length && { include: defaultInclude }),
76
- ...q,
77
- });
78
-
79
-
80
- const buildDefaultInclude = schema => Object.keys(schema.properties || {}).reduce(
81
- (memo, key) => (
82
- (
83
- schema.properties[key].$ref
84
- || (
85
- Array.isArray(schema.properties[key].anyOf)
86
- && schema.properties[key].anyOf[0].$ref
87
- )
88
- )
89
- ? { ...memo, [key]: true }
90
- : memo
91
- ),
92
- {},
93
- );
94
-
95
-
96
74
  const serializeData = (data, schema) => {
97
75
  const hasInputProps = Array.isArray(schema.inputProps);
98
76
  const payload = Object.keys(data).reduce(
@@ -133,17 +111,15 @@ export const createModel = (baseUrl, state, collectionName, schema = {}) => {
133
111
  const primaryKey = schema.primaryKey || 'id';
134
112
  const validator = createValidator(schema);
135
113
  const buildURL = createBuildURL(collectionName);
136
- const defaultInclude = buildDefaultInclude(schema);
137
- const buildQuery = createBuildQuery(defaultInclude);
138
114
  const req = (...args) => createClient(baseUrl, state.authUser)(...args);
139
115
  const create = q => req(buildURL(), {
140
116
  method: 'POST',
141
- body: buildQuery(Object.assign(q, { data: serializeData(q.data, schema) })),
117
+ body: Object.assign(q, { data: serializeData(q.data, schema) }),
142
118
  });
143
119
 
144
120
  const put = q => req(buildURL(q.where[primaryKey]), {
145
121
  method: 'PUT',
146
- body: buildQuery(Object.assign(q, { data: serializeData(q.data, schema) })),
122
+ body: Object.assign(q, { data: serializeData(q.data, schema) }),
147
123
  });
148
124
 
149
125
  const parse = data => {
@@ -172,14 +148,11 @@ export const createModel = (baseUrl, state, collectionName, schema = {}) => {
172
148
  get schema() {
173
149
  return schema;
174
150
  },
175
- get include() {
176
- return defaultInclude;
177
- },
178
151
  validateAttr: validator.validateAttr,
179
152
  validate: validator.validate,
180
- findMany: q => req(buildURL(null, buildQuery(q)))
153
+ findMany: q => req(buildURL(null, q))
181
154
  .then(results => results.map(parse)),
182
- findById: (id, q) => req(buildURL(id, buildQuery(q)))
155
+ findById: (id, q) => req(buildURL(id, q))
183
156
  .then(raw => !!raw ? parse(raw) : raw),
184
157
  create,
185
158
  update: put,
package/lib/model.spec.js CHANGED
@@ -101,7 +101,6 @@ describe('model.update(options)', () => {
101
101
  body: {
102
102
  where: { id: 1 },
103
103
  data: {},
104
- include: { signupCohort: true },
105
104
  },
106
105
  method: 'PUT',
107
106
  });
package/package.json CHANGED
@@ -1,24 +1,33 @@
1
1
  {
2
2
  "name": "@laboratoria/sdk-js",
3
- "version": "0.2.0",
3
+ "version": "1.0.0",
4
4
  "description": "Laboratoria JavaScript (browser) SDK",
5
5
  "scripts": {
6
- "test": "jest --verbose --coverage"
6
+ "test": "jest --verbose --coverage",
7
+ "changelog": "git log $(git describe --tags --abbrev=0)..HEAD --oneline --format=\"* %h %s (%an)\""
7
8
  },
8
9
  "license": "MIT",
9
10
  "dependencies": {
10
11
  "blueimp-md5": "^2.19.0",
11
- "firebase": "^9.6.2"
12
+ "firebase": "^9.6.4"
12
13
  },
13
14
  "devDependencies": {
14
- "@babel/core": "^7.16.7",
15
+ "@babel/core": "^7.16.12",
15
16
  "@babel/plugin-transform-modules-commonjs": "^7.16.8",
16
17
  "babel-jest": "^27.4.6",
17
18
  "jest": "^27.4.7",
18
- "webpack": "^5.65.0",
19
- "webpack-cli": "^4.9.1"
19
+ "webpack": "^5.67.0",
20
+ "webpack-cli": "^4.9.2"
20
21
  },
21
22
  "jest": {
22
- "testEnvironment": "jsdom"
23
+ "testEnvironment": "jsdom",
24
+ "coverageThreshold": {
25
+ "global": {
26
+ "statements": 96,
27
+ "branches": 91,
28
+ "functions": 98,
29
+ "lines": 96
30
+ }
31
+ }
23
32
  }
24
- }
33
+ }
package/schemas/core.json CHANGED
@@ -1,6 +1,23 @@
1
1
  {
2
2
  "$schema": "http://json-schema.org/draft-07/schema#",
3
3
  "definitions": {
4
+ "Country": {
5
+ "type": "object",
6
+ "properties": {
7
+ "code": {
8
+ "type": "string"
9
+ },
10
+ "name": {
11
+ "type": "string"
12
+ },
13
+ "contracts": {
14
+ "type": "array",
15
+ "items": {
16
+ "$ref": "#/definitions/Contract"
17
+ }
18
+ }
19
+ }
20
+ },
4
21
  "User": {
5
22
  "type": "object",
6
23
  "properties": {
@@ -99,6 +116,18 @@
99
116
  "type": "null"
100
117
  }
101
118
  ]
119
+ },
120
+ "contracts": {
121
+ "type": "array",
122
+ "items": {
123
+ "$ref": "#/definitions/Contract"
124
+ }
125
+ },
126
+ "gigs": {
127
+ "type": "array",
128
+ "items": {
129
+ "$ref": "#/definitions/Gig"
130
+ }
102
131
  }
103
132
  }
104
133
  },
@@ -270,20 +299,26 @@
270
299
  "$ref": "#/definitions/Dropout"
271
300
  }
272
301
  },
302
+ "gigs": {
303
+ "type": "array",
304
+ "items": {
305
+ "$ref": "#/definitions/Gig"
306
+ }
307
+ },
273
308
  "links": {
274
309
  "type": "array",
275
310
  "items": {
276
311
  "$ref": "#/definitions/CohortLink"
277
312
  }
278
313
  },
279
- "legacySlug": {
280
- "type": "string"
281
- },
282
314
  "signupUsers": {
283
315
  "type": "array",
284
316
  "items": {
285
317
  "$ref": "#/definitions/User"
286
318
  }
319
+ },
320
+ "legacySlug": {
321
+ "type": "string"
287
322
  }
288
323
  }
289
324
  },
@@ -307,7 +342,7 @@
307
342
  "null"
308
343
  ]
309
344
  },
310
- "studentCode": {
345
+ "legacyStudentCode": {
311
346
  "type": [
312
347
  "string",
313
348
  "null"
@@ -415,10 +450,133 @@
415
450
  "$ref": "#/definitions/User"
416
451
  }
417
452
  }
453
+ },
454
+ "Contract": {
455
+ "type": "object",
456
+ "properties": {
457
+ "id": {
458
+ "type": "integer"
459
+ },
460
+ "createdAt": {
461
+ "type": "string",
462
+ "format": "date-time"
463
+ },
464
+ "updatedAt": {
465
+ "type": "string",
466
+ "format": "date-time"
467
+ },
468
+ "createdBy": {
469
+ "type": "string"
470
+ },
471
+ "start": {
472
+ "type": "string",
473
+ "format": "date-time"
474
+ },
475
+ "end": {
476
+ "type": [
477
+ "string",
478
+ "null"
479
+ ],
480
+ "format": "date-time"
481
+ },
482
+ "hoursPerWeek": {
483
+ "type": "integer"
484
+ },
485
+ "isEmployment": {
486
+ "type": "boolean"
487
+ },
488
+ "currency": {
489
+ "type": "string",
490
+ "enum": [
491
+ "BRL",
492
+ "CLP",
493
+ "COP",
494
+ "MXN",
495
+ "PEN",
496
+ "USD"
497
+ ]
498
+ },
499
+ "feeBasis": {
500
+ "type": "string",
501
+ "enum": [
502
+ "HOURLY",
503
+ "MONTHLY"
504
+ ]
505
+ },
506
+ "feeAmount": {
507
+ "type": "integer"
508
+ },
509
+ "user": {
510
+ "$ref": "#/definitions/User"
511
+ },
512
+ "country": {
513
+ "$ref": "#/definitions/Country"
514
+ },
515
+ "gigs": {
516
+ "type": "array",
517
+ "items": {
518
+ "$ref": "#/definitions/Gig"
519
+ }
520
+ }
521
+ }
522
+ },
523
+ "Gig": {
524
+ "type": "object",
525
+ "properties": {
526
+ "id": {
527
+ "type": "integer"
528
+ },
529
+ "createdAt": {
530
+ "type": "string",
531
+ "format": "date-time"
532
+ },
533
+ "updatedAt": {
534
+ "type": "string",
535
+ "format": "date-time"
536
+ },
537
+ "createdBy": {
538
+ "type": "string"
539
+ },
540
+ "start": {
541
+ "type": "string",
542
+ "format": "date-time"
543
+ },
544
+ "end": {
545
+ "type": [
546
+ "string",
547
+ "null"
548
+ ],
549
+ "format": "date-time"
550
+ },
551
+ "hoursPerWeek": {
552
+ "type": "integer"
553
+ },
554
+ "role": {
555
+ "type": "string",
556
+ "enum": [
557
+ "bm",
558
+ "pdc",
559
+ "js",
560
+ "ux"
561
+ ]
562
+ },
563
+ "user": {
564
+ "$ref": "#/definitions/User"
565
+ },
566
+ "contract": {
567
+ "$ref": "#/definitions/Contract"
568
+ },
569
+ "cohort": {
570
+ "$ref": "#/definitions/Cohort"
571
+ }
572
+ }
418
573
  }
419
574
  },
420
575
  "type": "object",
421
576
  "properties": {
577
+ "country": {
578
+ "$ref": "#/definitions/Country"
579
+ },
422
580
  "user": {
423
581
  "$ref": "#/definitions/User"
424
582
  },
@@ -442,6 +600,12 @@
442
600
  },
443
601
  "dropout": {
444
602
  "$ref": "#/definitions/Dropout"
603
+ },
604
+ "contract": {
605
+ "$ref": "#/definitions/Contract"
606
+ },
607
+ "gig": {
608
+ "$ref": "#/definitions/Gig"
445
609
  }
446
610
  }
447
611
  }
package/lib/team.js DELETED
@@ -1,52 +0,0 @@
1
- import { createModels, extendSchemaDefinitions } from './model';
2
- import currencies from './currencies';
3
- import roles from './roles';
4
- import schema from '../schemas/team.json';
5
-
6
- const extended = {
7
- Country: {
8
- plural: 'countries',
9
- },
10
- Contract: {
11
- inputProps: [
12
- 'uid',
13
- 'countryCode',
14
- 'currency',
15
- 'isEmployment',
16
- 'feeBasis',
17
- 'feeAmount',
18
- 'hoursPerWeek',
19
- 'start',
20
- 'end',
21
- ],
22
- properties: {
23
- countryCode: {
24
- enum: ['BR', 'CL', 'CO', 'MX', 'PE'],
25
- },
26
- currency: {
27
- enum: currencies,
28
- },
29
- },
30
- },
31
- Gig: {
32
- inputProps: [
33
- // 'contract',
34
- 'cohortId',
35
- 'uid',
36
- 'role',
37
- 'hoursPerWeek',
38
- 'start',
39
- 'end',
40
- ],
41
- properties: {
42
- role: {
43
- enum: roles,
44
- },
45
- },
46
- },
47
- };
48
-
49
- export const createAPI = (url, state) => createModels(url, state, {
50
- ...schema,
51
- definitions: extendSchemaDefinitions(schema, extended),
52
- });
package/schemas/team.json DELETED
@@ -1,146 +0,0 @@
1
- {
2
- "$schema": "http://json-schema.org/draft-07/schema#",
3
- "definitions": {
4
- "Country": {
5
- "type": "object",
6
- "properties": {
7
- "code": {
8
- "type": "string"
9
- },
10
- "name": {
11
- "type": "string"
12
- },
13
- "contracts": {
14
- "type": "array",
15
- "items": {
16
- "$ref": "#/definitions/Contract"
17
- }
18
- }
19
- }
20
- },
21
- "Contract": {
22
- "type": "object",
23
- "properties": {
24
- "id": {
25
- "type": "integer"
26
- },
27
- "createdAt": {
28
- "type": "string",
29
- "format": "date-time"
30
- },
31
- "updatedAt": {
32
- "type": "string",
33
- "format": "date-time"
34
- },
35
- "createdBy": {
36
- "type": "string"
37
- },
38
- "uid": {
39
- "type": "string"
40
- },
41
- "isEmployment": {
42
- "type": "boolean"
43
- },
44
- "currency": {
45
- "type": "string"
46
- },
47
- "feeBasis": {
48
- "type": "string",
49
- "enum": [
50
- "HOURLY",
51
- "MONTHLY"
52
- ]
53
- },
54
- "feeAmount": {
55
- "type": "integer"
56
- },
57
- "hoursPerWeek": {
58
- "type": "integer"
59
- },
60
- "start": {
61
- "type": "string",
62
- "format": "date-time"
63
- },
64
- "end": {
65
- "type": [
66
- "string",
67
- "null"
68
- ],
69
- "format": "date-time"
70
- },
71
- "country": {
72
- "$ref": "#/definitions/Country"
73
- },
74
- "gigs": {
75
- "type": "array",
76
- "items": {
77
- "$ref": "#/definitions/Gig"
78
- }
79
- }
80
- }
81
- },
82
- "Gig": {
83
- "type": "object",
84
- "properties": {
85
- "id": {
86
- "type": "integer"
87
- },
88
- "createdAt": {
89
- "type": "string",
90
- "format": "date-time"
91
- },
92
- "updatedAt": {
93
- "type": "string",
94
- "format": "date-time"
95
- },
96
- "createdBy": {
97
- "type": "string"
98
- },
99
- "role": {
100
- "type": "string",
101
- "enum": [
102
- "bm",
103
- "pdc",
104
- "js",
105
- "ux"
106
- ]
107
- },
108
- "hoursPerWeek": {
109
- "type": "integer"
110
- },
111
- "start": {
112
- "type": "string",
113
- "format": "date-time"
114
- },
115
- "end": {
116
- "type": [
117
- "string",
118
- "null"
119
- ],
120
- "format": "date-time"
121
- },
122
- "uid": {
123
- "type": "string"
124
- },
125
- "cohortId": {
126
- "type": "integer"
127
- },
128
- "contract": {
129
- "$ref": "#/definitions/Contract"
130
- }
131
- }
132
- }
133
- },
134
- "type": "object",
135
- "properties": {
136
- "country": {
137
- "$ref": "#/definitions/Country"
138
- },
139
- "contract": {
140
- "$ref": "#/definitions/Contract"
141
- },
142
- "gig": {
143
- "$ref": "#/definitions/Gig"
144
- }
145
- }
146
- }