projects.js 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676
  1. 'use strict'
  2. const Blob = require('overleaf-editor-core').Blob
  3. exports.paths = {
  4. '/projects': {
  5. post: {
  6. 'x-swagger-router-controller': 'projects',
  7. operationId: 'initializeProject',
  8. tags: ['Project'],
  9. description: 'Initialize project.',
  10. consumes: ['application/json'],
  11. parameters: [
  12. {
  13. name: 'body',
  14. in: 'body',
  15. schema: {
  16. type: 'object',
  17. properties: {
  18. projectId: { type: 'string' },
  19. },
  20. },
  21. },
  22. ],
  23. responses: {
  24. 200: {
  25. description: 'Initialized',
  26. schema: {
  27. $ref: '#/definitions/Project',
  28. },
  29. },
  30. },
  31. security: [
  32. {
  33. basic: [],
  34. },
  35. ],
  36. },
  37. },
  38. '/projects/blob-stats': {
  39. post: {
  40. 'x-swagger-router-controller': 'projects',
  41. operationId: 'getProjectBlobsStats',
  42. tags: ['Project'],
  43. description: 'Get Blob stats for projects.',
  44. consumes: ['application/json'],
  45. parameters: [
  46. {
  47. name: 'body',
  48. in: 'body',
  49. schema: {
  50. type: 'object',
  51. properties: {
  52. projectIds: {
  53. type: 'array',
  54. items: { type: 'string' },
  55. },
  56. },
  57. },
  58. },
  59. ],
  60. responses: {
  61. 200: {
  62. description: 'Initialized',
  63. schema: {
  64. type: 'array',
  65. items: {
  66. $ref: '#/definitions/ProjectBlobStats',
  67. },
  68. },
  69. },
  70. },
  71. security: [
  72. {
  73. basic: [],
  74. },
  75. ],
  76. },
  77. },
  78. '/projects/{project_id}/blob-stats': {
  79. post: {
  80. 'x-swagger-router-controller': 'projects',
  81. operationId: 'getBlobStats',
  82. tags: ['Project'],
  83. description: 'Get specific blob stats for a project.',
  84. consumes: ['application/json'],
  85. parameters: [
  86. {
  87. name: 'project_id',
  88. in: 'path',
  89. description: 'project id',
  90. required: true,
  91. type: 'string',
  92. },
  93. {
  94. name: 'body',
  95. in: 'body',
  96. required: true,
  97. schema: {
  98. type: 'object',
  99. properties: {
  100. blobHashes: {
  101. type: 'array',
  102. items: {
  103. type: 'string',
  104. },
  105. },
  106. },
  107. required: ['blobHashes'],
  108. },
  109. },
  110. ],
  111. responses: {
  112. 200: {
  113. description: 'Success',
  114. schema: {
  115. $ref: '#/definitions/ProjectBlobStats',
  116. },
  117. },
  118. },
  119. security: [
  120. {
  121. basic: [],
  122. },
  123. ],
  124. },
  125. },
  126. '/projects/{project_id}': {
  127. delete: {
  128. 'x-swagger-router-controller': 'projects',
  129. operationId: 'deleteProject',
  130. tags: ['Project'],
  131. description: "Delete a project's history",
  132. parameters: [
  133. {
  134. name: 'project_id',
  135. in: 'path',
  136. description: 'project id',
  137. required: true,
  138. type: 'string',
  139. },
  140. ],
  141. responses: {
  142. 204: {
  143. description: 'Success',
  144. },
  145. },
  146. security: [
  147. {
  148. basic: [],
  149. },
  150. ],
  151. },
  152. },
  153. '/projects/{project_id}/blobs/{hash}': {
  154. get: {
  155. 'x-swagger-router-controller': 'projects',
  156. operationId: 'getProjectBlob',
  157. tags: ['Project'],
  158. description: 'Fetch blob content by its project id and hash.',
  159. parameters: [
  160. {
  161. name: 'project_id',
  162. in: 'path',
  163. description: 'project id',
  164. required: true,
  165. type: 'string',
  166. },
  167. {
  168. name: 'hash',
  169. in: 'path',
  170. description: 'Hexadecimal SHA-1 hash',
  171. required: true,
  172. type: 'string',
  173. pattern: Blob.HEX_HASH_RX_STRING,
  174. },
  175. {
  176. name: 'range',
  177. in: 'header',
  178. description: 'HTTP Range header',
  179. required: false,
  180. type: 'string',
  181. },
  182. ],
  183. produces: ['application/octet-stream'],
  184. responses: {
  185. 200: {
  186. description: 'Success',
  187. schema: {
  188. type: 'file',
  189. },
  190. },
  191. 404: {
  192. description: 'Not Found',
  193. schema: {
  194. $ref: '#/definitions/Error',
  195. },
  196. },
  197. },
  198. security: [{ jwt: [] }, { token: [] }],
  199. },
  200. head: {
  201. 'x-swagger-router-controller': 'projects',
  202. operationId: 'headProjectBlob',
  203. tags: ['Project'],
  204. description: 'Fetch blob content-length by its project id and hash.',
  205. parameters: [
  206. {
  207. name: 'project_id',
  208. in: 'path',
  209. description: 'project id',
  210. required: true,
  211. type: 'string',
  212. },
  213. {
  214. name: 'hash',
  215. in: 'path',
  216. description: 'Hexadecimal SHA-1 hash',
  217. required: true,
  218. type: 'string',
  219. pattern: Blob.HEX_HASH_RX_STRING,
  220. },
  221. ],
  222. produces: ['application/octet-stream'],
  223. responses: {
  224. 200: {
  225. description: 'Success',
  226. schema: {
  227. type: 'file',
  228. },
  229. },
  230. 404: {
  231. description: 'Not Found',
  232. schema: {
  233. $ref: '#/definitions/Error',
  234. },
  235. },
  236. },
  237. security: [{ jwt: [] }, { token: [] }],
  238. },
  239. put: {
  240. 'x-swagger-router-controller': 'projects',
  241. operationId: 'createProjectBlob',
  242. tags: ['Project'],
  243. description:
  244. 'Create blob to be used in a file addition operation when importing a' +
  245. ' snapshot or changes',
  246. parameters: [
  247. {
  248. name: 'project_id',
  249. in: 'path',
  250. description: 'project id',
  251. required: true,
  252. type: 'string',
  253. },
  254. {
  255. name: 'hash',
  256. in: 'path',
  257. description: 'Hexadecimal SHA-1 hash',
  258. required: true,
  259. type: 'string',
  260. pattern: Blob.HEX_HASH_RX_STRING,
  261. },
  262. ],
  263. responses: {
  264. 201: {
  265. description: 'Created',
  266. },
  267. },
  268. },
  269. post: {
  270. 'x-swagger-router-controller': 'projects',
  271. operationId: 'copyProjectBlob',
  272. tags: ['Project'],
  273. description:
  274. 'Copies a blob from a source project to a target project when duplicating a project',
  275. parameters: [
  276. {
  277. name: 'project_id',
  278. in: 'path',
  279. description: 'target project id',
  280. required: true,
  281. type: 'string',
  282. },
  283. {
  284. name: 'hash',
  285. in: 'path',
  286. description: 'Hexadecimal SHA-1 hash',
  287. required: true,
  288. type: 'string',
  289. pattern: Blob.HEX_HASH_RX_STRING,
  290. },
  291. {
  292. name: 'copyFrom',
  293. in: 'query',
  294. description: 'source project id',
  295. required: true,
  296. type: 'string',
  297. },
  298. ],
  299. responses: {
  300. 201: {
  301. description: 'Created',
  302. },
  303. },
  304. },
  305. },
  306. '/projects/{project_id}/latest/content': {
  307. get: {
  308. 'x-swagger-router-controller': 'projects',
  309. operationId: 'getLatestContent',
  310. tags: ['Project'],
  311. description:
  312. 'Get full content of the latest version. Text file ' +
  313. 'content is included, but binary files are just linked by hash.',
  314. parameters: [
  315. {
  316. name: 'project_id',
  317. in: 'path',
  318. description: 'project id',
  319. required: true,
  320. type: 'string',
  321. },
  322. ],
  323. responses: {
  324. 200: {
  325. description: 'Success',
  326. schema: {
  327. $ref: '#/definitions/Snapshot',
  328. },
  329. },
  330. 404: {
  331. description: 'Not Found',
  332. schema: {
  333. $ref: '#/definitions/Error',
  334. },
  335. },
  336. },
  337. },
  338. },
  339. '/projects/{project_id}/latest/hashed_content': {
  340. get: {
  341. 'x-swagger-router-controller': 'projects',
  342. operationId: 'getLatestHashedContent',
  343. tags: ['Project'],
  344. description:
  345. 'Get a snapshot of a project at the latest version ' +
  346. 'with the hashes for the contents each file',
  347. parameters: [
  348. {
  349. name: 'project_id',
  350. in: 'path',
  351. description: 'project id',
  352. required: true,
  353. type: 'string',
  354. },
  355. ],
  356. responses: {
  357. 200: {
  358. description: 'Success',
  359. schema: {
  360. $ref: '#/definitions/Snapshot',
  361. },
  362. },
  363. 404: {
  364. description: 'Not Found',
  365. schema: {
  366. $ref: '#/definitions/Error',
  367. },
  368. },
  369. },
  370. security: [
  371. {
  372. basic: [],
  373. },
  374. ],
  375. },
  376. },
  377. '/projects/{project_id}/latest/history': {
  378. get: {
  379. 'x-swagger-router-controller': 'projects',
  380. operationId: 'getLatestHistory',
  381. tags: ['Project'],
  382. description:
  383. 'Get the latest sequence of changes.' +
  384. ' TODO probably want a configurable depth.',
  385. parameters: [
  386. {
  387. name: 'project_id',
  388. in: 'path',
  389. description: 'project id',
  390. required: true,
  391. type: 'string',
  392. },
  393. ],
  394. responses: {
  395. 200: {
  396. description: 'Success',
  397. schema: {
  398. $ref: '#/definitions/ChunkResponse',
  399. },
  400. },
  401. 404: {
  402. description: 'Not Found',
  403. schema: {
  404. $ref: '#/definitions/Error',
  405. },
  406. },
  407. },
  408. },
  409. },
  410. '/projects/{project_id}/latest/history/raw': {
  411. get: {
  412. 'x-swagger-router-controller': 'projects',
  413. operationId: 'getLatestHistoryRaw',
  414. tags: ['Project'],
  415. description: 'Get the metadata of latest sequence of changes.',
  416. parameters: [
  417. {
  418. name: 'project_id',
  419. in: 'path',
  420. description: 'project id',
  421. required: true,
  422. type: 'string',
  423. },
  424. {
  425. name: 'readOnly',
  426. in: 'query',
  427. description: 'use read only database connection',
  428. required: false,
  429. type: 'boolean',
  430. },
  431. ],
  432. responses: {
  433. 200: {
  434. description: 'Success',
  435. schema: {
  436. $ref: '#/definitions/ChunkResponseRaw',
  437. },
  438. },
  439. 404: {
  440. description: 'Not Found',
  441. schema: {
  442. $ref: '#/definitions/Error',
  443. },
  444. },
  445. },
  446. },
  447. },
  448. '/projects/{project_id}/latest/persistedHistory': {
  449. get: {
  450. 'x-swagger-router-controller': 'projects',
  451. operationId: 'getLatestPersistedHistory',
  452. tags: ['Project'],
  453. description: 'Get the latest sequence of changes.',
  454. parameters: [
  455. {
  456. name: 'project_id',
  457. in: 'path',
  458. description: 'project id',
  459. required: true,
  460. type: 'string',
  461. },
  462. ],
  463. responses: {
  464. 200: {
  465. description: 'Success',
  466. schema: {
  467. $ref: '#/definitions/ChunkResponse',
  468. },
  469. },
  470. 404: {
  471. description: 'Not Found',
  472. schema: {
  473. $ref: '#/definitions/Error',
  474. },
  475. },
  476. },
  477. },
  478. },
  479. '/projects/{project_id}/versions/{version}/history': {
  480. get: {
  481. 'x-swagger-router-controller': 'projects',
  482. operationId: 'getHistory',
  483. tags: ['Project'],
  484. description:
  485. 'Get the sequence of changes that includes the given version.',
  486. parameters: [
  487. {
  488. name: 'project_id',
  489. in: 'path',
  490. description: 'project id',
  491. required: true,
  492. type: 'string',
  493. },
  494. {
  495. name: 'version',
  496. in: 'path',
  497. description: 'numeric version',
  498. required: true,
  499. type: 'number',
  500. },
  501. ],
  502. responses: {
  503. 200: {
  504. description: 'Success',
  505. schema: {
  506. $ref: '#/definitions/ChunkResponse',
  507. },
  508. },
  509. 404: {
  510. description: 'Not Found',
  511. schema: {
  512. $ref: '#/definitions/Error',
  513. },
  514. },
  515. },
  516. },
  517. },
  518. '/projects/{project_id}/versions/{version}/content': {
  519. get: {
  520. 'x-swagger-router-controller': 'projects',
  521. operationId: 'getContentAtVersion',
  522. tags: ['Project'],
  523. description: 'Get full content at the given version',
  524. parameters: [
  525. {
  526. name: 'project_id',
  527. in: 'path',
  528. description: 'project id',
  529. required: true,
  530. type: 'string',
  531. },
  532. {
  533. name: 'version',
  534. in: 'path',
  535. description: 'numeric version',
  536. required: true,
  537. type: 'number',
  538. },
  539. ],
  540. responses: {
  541. 200: {
  542. description: 'Success',
  543. schema: {
  544. $ref: '#/definitions/Snapshot',
  545. },
  546. },
  547. 404: {
  548. description: 'Not Found',
  549. schema: {
  550. $ref: '#/definitions/Error',
  551. },
  552. },
  553. },
  554. },
  555. },
  556. '/projects/{project_id}/timestamp/{timestamp}/history': {
  557. get: {
  558. 'x-swagger-router-controller': 'projects',
  559. operationId: 'getHistoryBefore',
  560. tags: ['Project'],
  561. description:
  562. 'Get the sequence of changes. ' + ' before the given timestamp',
  563. parameters: [
  564. {
  565. name: 'project_id',
  566. in: 'path',
  567. description: 'project id',
  568. required: true,
  569. type: 'string',
  570. },
  571. {
  572. name: 'timestamp',
  573. in: 'path',
  574. description: 'timestamp',
  575. required: true,
  576. type: 'string',
  577. format: 'date-time',
  578. },
  579. ],
  580. responses: {
  581. 200: {
  582. description: 'Success',
  583. schema: {
  584. $ref: '#/definitions/ChunkResponse',
  585. },
  586. },
  587. 404: {
  588. description: 'Not Found',
  589. schema: {
  590. $ref: '#/definitions/Error',
  591. },
  592. },
  593. },
  594. },
  595. },
  596. '/projects/{project_id}/version/{version}/zip': {
  597. get: {
  598. 'x-swagger-router-controller': 'projects',
  599. operationId: 'getZip',
  600. tags: ['Project'],
  601. description: 'Download zip with project content',
  602. parameters: [
  603. {
  604. name: 'project_id',
  605. in: 'path',
  606. description: 'project id',
  607. required: true,
  608. type: 'string',
  609. },
  610. {
  611. name: 'version',
  612. in: 'path',
  613. description: 'numeric version',
  614. required: true,
  615. type: 'number',
  616. },
  617. ],
  618. produces: ['application/octet-stream'],
  619. responses: {
  620. 200: {
  621. description: 'success',
  622. },
  623. 404: {
  624. description: 'not found',
  625. },
  626. },
  627. security: [
  628. {
  629. token: [],
  630. },
  631. ],
  632. },
  633. post: {
  634. 'x-swagger-router-controller': 'projects',
  635. operationId: 'createZip',
  636. tags: ['Project'],
  637. description:
  638. 'Create a zip file with project content. Returns a link to be polled.',
  639. parameters: [
  640. {
  641. name: 'project_id',
  642. in: 'path',
  643. description: 'project id',
  644. required: true,
  645. type: 'string',
  646. },
  647. {
  648. name: 'version',
  649. in: 'path',
  650. description: 'numeric version',
  651. required: true,
  652. type: 'number',
  653. },
  654. ],
  655. responses: {
  656. 200: {
  657. description: 'success',
  658. schema: {
  659. $ref: '#/definitions/ZipInfo',
  660. },
  661. },
  662. 404: {
  663. description: 'not found',
  664. },
  665. },
  666. security: [
  667. {
  668. basic: [],
  669. },
  670. ],
  671. },
  672. },
  673. }