Merge branch 'master' of http://35.207.205.18:3000/Arminta/watermanagement-backend
commit
127251e2eb
@ -0,0 +1 @@
|
||||
../google-p12-pem/build/src/bin/gp12-pem.js
|
||||
@ -0,0 +1,219 @@
|
||||
# Changelog
|
||||
|
||||
[npm history][1]
|
||||
|
||||
[1]: https://www.npmjs.com/package/nodejs-paginator?activeTab=versions
|
||||
|
||||
### [3.0.7](https://github.com/googleapis/nodejs-paginator/compare/v3.0.6...v3.0.7) (2022-02-14)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* update signature of end to comply with update node types definition ([#311](https://github.com/googleapis/nodejs-paginator/issues/311)) ([79e6fbd](https://github.com/googleapis/nodejs-paginator/commit/79e6fbdae5008d874613d2919a6cf723708fc919))
|
||||
|
||||
### [3.0.6](https://www.github.com/googleapis/nodejs-paginator/compare/v3.0.5...v3.0.6) (2021-09-09)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **build:** switch primary branch to main ([#287](https://www.github.com/googleapis/nodejs-paginator/issues/287)) ([1b796f3](https://www.github.com/googleapis/nodejs-paginator/commit/1b796f3377174354a62b7475d16f52213197f650))
|
||||
|
||||
### [3.0.5](https://www.github.com/googleapis/nodejs-paginator/compare/v3.0.4...v3.0.5) (2020-09-02)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* add configs by running synthtool ([#241](https://www.github.com/googleapis/nodejs-paginator/issues/241)) ([643593a](https://www.github.com/googleapis/nodejs-paginator/commit/643593ae9ffb8febff69a7bdae19239f5bcb1266))
|
||||
|
||||
### [3.0.4](https://www.github.com/googleapis/nodejs-paginator/compare/v3.0.3...v3.0.4) (2020-08-06)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* destroy ResourceStream with pre-flight error ([#236](https://www.github.com/googleapis/nodejs-paginator/issues/236)) ([d57beb4](https://www.github.com/googleapis/nodejs-paginator/commit/d57beb424d875a7bf502d458cc208f1bbe47a42a))
|
||||
|
||||
### [3.0.3](https://www.github.com/googleapis/nodejs-paginator/compare/v3.0.2...v3.0.3) (2020-07-24)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* move gitattributes files to node templates ([#234](https://www.github.com/googleapis/nodejs-paginator/issues/234)) ([30e881c](https://www.github.com/googleapis/nodejs-paginator/commit/30e881ce7415749b93b6b7e4e71745ea3fb248b6))
|
||||
|
||||
### [3.0.2](https://www.github.com/googleapis/nodejs-paginator/compare/v3.0.1...v3.0.2) (2020-07-06)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* update node issue template ([#221](https://www.github.com/googleapis/nodejs-paginator/issues/221)) ([088153c](https://www.github.com/googleapis/nodejs-paginator/commit/088153c4fca6d53e2e5ef4bb42365ce5493b913d))
|
||||
|
||||
### [3.0.1](https://www.github.com/googleapis/nodejs-paginator/compare/v3.0.0...v3.0.1) (2020-05-20)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* apache license URL ([#468](https://www.github.com/googleapis/nodejs-paginator/issues/468)) ([#211](https://www.github.com/googleapis/nodejs-paginator/issues/211)) ([f343b7f](https://www.github.com/googleapis/nodejs-paginator/commit/f343b7f7e184fd1b453f20ac1463d17520aac7ad))
|
||||
|
||||
## [3.0.0](https://www.github.com/googleapis/nodejs-paginator/compare/v2.0.3...v3.0.0) (2020-03-25)
|
||||
|
||||
|
||||
### ⚠ BREAKING CHANGES
|
||||
|
||||
* **dep:** upgrade gts 2.0.0 (#194)
|
||||
* **deps:** deprecated node 8 to 10; upgrade typescript
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **dep:** upgrade gts 2.0.0 ([#194](https://www.github.com/googleapis/nodejs-paginator/issues/194)) ([4eaf9be](https://www.github.com/googleapis/nodejs-paginator/commit/4eaf9bed1fcfd0f10e877ff15c1d0e968e3356c8))
|
||||
* **deps:** deprecated node 8 to 10; upgrade typescript ([f6434ab](https://www.github.com/googleapis/nodejs-paginator/commit/f6434ab9cacb6ab804c070f19c38b6072ca326b5))
|
||||
|
||||
### [2.0.3](https://www.github.com/googleapis/nodejs-paginator/compare/v2.0.2...v2.0.3) (2019-12-05)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **deps:** pin TypeScript below 3.7.0 ([e06e1b0](https://www.github.com/googleapis/nodejs-paginator/commit/e06e1b0a2e2bb1cf56fc806c1703b8b5e468b954))
|
||||
|
||||
### [2.0.2](https://www.github.com/googleapis/nodejs-paginator/compare/v2.0.1...v2.0.2) (2019-11-13)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **docs:** add jsdoc-region-tag plugin ([#155](https://www.github.com/googleapis/nodejs-paginator/issues/155)) ([b983799](https://www.github.com/googleapis/nodejs-paginator/commit/b98379905848fd179c6268aff3e1cfaf2bf76663))
|
||||
|
||||
### [2.0.1](https://www.github.com/googleapis/nodejs-paginator/compare/v2.0.0...v2.0.1) (2019-08-25)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **deps:** use the latest extend ([#141](https://www.github.com/googleapis/nodejs-paginator/issues/141)) ([61b383e](https://www.github.com/googleapis/nodejs-paginator/commit/61b383e))
|
||||
|
||||
## [2.0.0](https://www.github.com/googleapis/nodejs-paginator/compare/v1.0.2...v2.0.0) (2019-07-12)
|
||||
|
||||
|
||||
### ⚠ BREAKING CHANGES
|
||||
|
||||
* rewrite streaming logic (#136)
|
||||
|
||||
### Code Refactoring
|
||||
|
||||
* rewrite streaming logic ([#136](https://www.github.com/googleapis/nodejs-paginator/issues/136)) ([641d82d](https://www.github.com/googleapis/nodejs-paginator/commit/641d82d))
|
||||
|
||||
### [1.0.2](https://www.github.com/googleapis/nodejs-paginator/compare/v1.0.1...v1.0.2) (2019-06-26)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **docs:** link to reference docs section on googleapis.dev ([#132](https://www.github.com/googleapis/nodejs-paginator/issues/132)) ([be231be](https://www.github.com/googleapis/nodejs-paginator/commit/be231be))
|
||||
|
||||
### [1.0.1](https://www.github.com/googleapis/nodejs-paginator/compare/v1.0.0...v1.0.1) (2019-06-14)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **docs:** move to new client docs URL ([#129](https://www.github.com/googleapis/nodejs-paginator/issues/129)) ([689f483](https://www.github.com/googleapis/nodejs-paginator/commit/689f483))
|
||||
|
||||
## [1.0.0](https://www.github.com/googleapis/nodejs-paginator/compare/v0.2.0...v1.0.0) (2019-05-03)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **deps:** update dependency arrify to v2 ([#109](https://www.github.com/googleapis/nodejs-paginator/issues/109)) ([9f06c83](https://www.github.com/googleapis/nodejs-paginator/commit/9f06c83))
|
||||
|
||||
|
||||
### Build System
|
||||
|
||||
* upgrade engines field to >=8.10.0 ([#115](https://www.github.com/googleapis/nodejs-paginator/issues/115)) ([0921076](https://www.github.com/googleapis/nodejs-paginator/commit/0921076))
|
||||
|
||||
|
||||
### BREAKING CHANGES
|
||||
|
||||
* upgrade engines field to >=8.10.0 (#115)
|
||||
|
||||
## v0.2.0
|
||||
|
||||
03-08-2019 12:15 PST
|
||||
|
||||
### New Features
|
||||
- feat: handle promise based functions ([#91](https://github.com/googleapis/nodejs-paginator/pull/91))
|
||||
- refactor(ts): create generic for object streams ([#101](https://github.com/googleapis/nodejs-paginator/pull/101))
|
||||
|
||||
### Dependencies
|
||||
- chore(deps): update dependency through2 to v3 ([#53](https://github.com/googleapis/nodejs-paginator/pull/53))
|
||||
- chore(deps): update dependency @types/is to v0.0.21 ([#55](https://github.com/googleapis/nodejs-paginator/pull/55))
|
||||
- chore(deps): update dependency gts to ^0.9.0 ([#57](https://github.com/googleapis/nodejs-paginator/pull/57))
|
||||
- fix: Pin @types/sinon to last compatible version ([#61](https://github.com/googleapis/nodejs-paginator/pull/61))
|
||||
- refactor: trim a few dependencies ([#60](https://github.com/googleapis/nodejs-paginator/pull/60))
|
||||
- chore(deps): update dependency @types/sinon to v5.0.7 ([#62](https://github.com/googleapis/nodejs-paginator/pull/62))
|
||||
- chore(deps): update dependency @types/sinon to v7 ([#81](https://github.com/googleapis/nodejs-paginator/pull/81))
|
||||
- chore(deps): update dependency mocha to v6
|
||||
|
||||
### Documentation
|
||||
- docs: add lint/fix example to contributing guide ([#85](https://github.com/googleapis/nodejs-paginator/pull/85))
|
||||
- chore: move CONTRIBUTING.md to root ([#87](https://github.com/googleapis/nodejs-paginator/pull/87))
|
||||
- docs: update links in contrib guide ([#94](https://github.com/googleapis/nodejs-paginator/pull/94))
|
||||
- docs: update contributing path in README ([#88](https://github.com/googleapis/nodejs-paginator/pull/88))
|
||||
|
||||
### Internal / Testing Changes
|
||||
- chore: include build in eslintignore ([#49](https://github.com/googleapis/nodejs-paginator/pull/49))
|
||||
- chore: update CircleCI config ([#52](https://github.com/googleapis/nodejs-paginator/pull/52))
|
||||
- chore: use latest npm on Windows ([#54](https://github.com/googleapis/nodejs-paginator/pull/54))
|
||||
- chore: update eslintignore config ([#56](https://github.com/googleapis/nodejs-paginator/pull/56))
|
||||
- chore: add synth.metadata
|
||||
- fix(build): fix system key decryption ([#64](https://github.com/googleapis/nodejs-paginator/pull/64))
|
||||
- chore: update license file ([#68](https://github.com/googleapis/nodejs-paginator/pull/68))
|
||||
- chore(build): update prettier config ([#69](https://github.com/googleapis/nodejs-paginator/pull/69))
|
||||
- chore: nyc ignore build/test by default ([#71](https://github.com/googleapis/nodejs-paginator/pull/71))
|
||||
- chore: always nyc report before calling codecov ([#72](https://github.com/googleapis/nodejs-paginator/pull/72))
|
||||
- build: add Kokoro configs for autorelease ([#75](https://github.com/googleapis/nodejs-paginator/pull/75))
|
||||
- fix(build): fix Kokoro release script ([#76](https://github.com/googleapis/nodejs-paginator/pull/76))
|
||||
- chore: fix publish.sh permission +x ([#77](https://github.com/googleapis/nodejs-paginator/pull/77))
|
||||
- chore: update nyc and eslint configs ([#79](https://github.com/googleapis/nodejs-paginator/pull/79))
|
||||
- chore(build): inject yoshi automation key ([#80](https://github.com/googleapis/nodejs-paginator/pull/80))
|
||||
- build: check broken links in generated docs ([#82](https://github.com/googleapis/nodejs-paginator/pull/82))
|
||||
- build: ignore googleapis.com in doc link check ([#84](https://github.com/googleapis/nodejs-paginator/pull/84))
|
||||
- build: test using @grpc/grpc-js in CI ([#89](https://github.com/googleapis/nodejs-paginator/pull/89))
|
||||
- build: create docs test npm scripts ([#90](https://github.com/googleapis/nodejs-paginator/pull/90))
|
||||
- build: use linkinator for docs test ([#93](https://github.com/googleapis/nodejs-paginator/pull/93))
|
||||
- build: update release configuration
|
||||
- build: fix types for sinon ([#98](https://github.com/googleapis/nodejs-paginator/pull/98))
|
||||
- build: use node10 to run samples-test, system-test etc ([#97](https://github.com/googleapis/nodejs-paginator/pull/97))
|
||||
- build: Add docuploader credentials to node publish jobs ([#99](https://github.com/googleapis/nodejs-paginator/pull/99))
|
||||
|
||||
## v0.1.2
|
||||
|
||||
### Bug fixes
|
||||
- fix: call limiter.makeRequest() instead of original method ([#43](https://github.com/googleapis/nodejs-paginator/pull/43))
|
||||
|
||||
### Internal / Testing Changes
|
||||
- chore: update issue templates ([#42](https://github.com/googleapis/nodejs-paginator/pull/42))
|
||||
- chore: remove old issue template ([#40](https://github.com/googleapis/nodejs-paginator/pull/40))
|
||||
- build: run tests on node11 ([#39](https://github.com/googleapis/nodejs-paginator/pull/39))
|
||||
- chores(build): run codecov on continuous builds ([#36](https://github.com/googleapis/nodejs-paginator/pull/36))
|
||||
- chores(build): do not collect sponge.xml from windows builds ([#37](https://github.com/googleapis/nodejs-paginator/pull/37))
|
||||
- chore: update new issue template ([#35](https://github.com/googleapis/nodejs-paginator/pull/35))
|
||||
- chore(deps): update dependency sinon to v7 ([#31](https://github.com/googleapis/nodejs-paginator/pull/31))
|
||||
- build: fix codecov uploading on Kokoro ([#32](https://github.com/googleapis/nodejs-paginator/pull/32))
|
||||
- Update kokoro config ([#29](https://github.com/googleapis/nodejs-paginator/pull/29))
|
||||
- Update CI config ([#27](https://github.com/googleapis/nodejs-paginator/pull/27))
|
||||
- Don't publish sourcemaps ([#25](https://github.com/googleapis/nodejs-paginator/pull/25))
|
||||
- build: prevent system/sample-test from leaking credentials
|
||||
- Update kokoro config ([#23](https://github.com/googleapis/nodejs-paginator/pull/23))
|
||||
- test: remove appveyor config ([#22](https://github.com/googleapis/nodejs-paginator/pull/22))
|
||||
- Update CI config ([#21](https://github.com/googleapis/nodejs-paginator/pull/21))
|
||||
- Enable prefer-const in the eslint config ([#20](https://github.com/googleapis/nodejs-paginator/pull/20))
|
||||
- Enable no-var in eslint ([#19](https://github.com/googleapis/nodejs-paginator/pull/19))
|
||||
- Update CI config ([#18](https://github.com/googleapis/nodejs-paginator/pull/18))
|
||||
|
||||
## v0.1.1
|
||||
|
||||
### Internal / Testing Changes
|
||||
- Add synth script and update CI config (#14)
|
||||
- chore(deps): update dependency nyc to v13 (#12)
|
||||
- chore: ignore package-lock.json (#11)
|
||||
- chore(deps): lock file maintenance (#10)
|
||||
- chore: update renovate config (#9)
|
||||
- remove that whitespace (#8)
|
||||
- chore(deps): lock file maintenance (#7)
|
||||
- chore(deps): update dependency typescript to v3 (#6)
|
||||
- chore: assert.deelEqual => assert.deepStrictEqual (#5)
|
||||
- chore: move mocha options to mocha.opts (#4)
|
||||
@ -0,0 +1,202 @@
|
||||
|
||||
Apache License
|
||||
Version 2.0, January 2004
|
||||
http://www.apache.org/licenses/
|
||||
|
||||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||
|
||||
1. Definitions.
|
||||
|
||||
"License" shall mean the terms and conditions for use, reproduction,
|
||||
and distribution as defined by Sections 1 through 9 of this document.
|
||||
|
||||
"Licensor" shall mean the copyright owner or entity authorized by
|
||||
the copyright owner that is granting the License.
|
||||
|
||||
"Legal Entity" shall mean the union of the acting entity and all
|
||||
other entities that control, are controlled by, or are under common
|
||||
control with that entity. For the purposes of this definition,
|
||||
"control" means (i) the power, direct or indirect, to cause the
|
||||
direction or management of such entity, whether by contract or
|
||||
otherwise, or (ii) ownership of fifty percent (50%) or more of the
|
||||
outstanding shares, or (iii) beneficial ownership of such entity.
|
||||
|
||||
"You" (or "Your") shall mean an individual or Legal Entity
|
||||
exercising permissions granted by this License.
|
||||
|
||||
"Source" form shall mean the preferred form for making modifications,
|
||||
including but not limited to software source code, documentation
|
||||
source, and configuration files.
|
||||
|
||||
"Object" form shall mean any form resulting from mechanical
|
||||
transformation or translation of a Source form, including but
|
||||
not limited to compiled object code, generated documentation,
|
||||
and conversions to other media types.
|
||||
|
||||
"Work" shall mean the work of authorship, whether in Source or
|
||||
Object form, made available under the License, as indicated by a
|
||||
copyright notice that is included in or attached to the work
|
||||
(an example is provided in the Appendix below).
|
||||
|
||||
"Derivative Works" shall mean any work, whether in Source or Object
|
||||
form, that is based on (or derived from) the Work and for which the
|
||||
editorial revisions, annotations, elaborations, or other modifications
|
||||
represent, as a whole, an original work of authorship. For the purposes
|
||||
of this License, Derivative Works shall not include works that remain
|
||||
separable from, or merely link (or bind by name) to the interfaces of,
|
||||
the Work and Derivative Works thereof.
|
||||
|
||||
"Contribution" shall mean any work of authorship, including
|
||||
the original version of the Work and any modifications or additions
|
||||
to that Work or Derivative Works thereof, that is intentionally
|
||||
submitted to Licensor for inclusion in the Work by the copyright owner
|
||||
or by an individual or Legal Entity authorized to submit on behalf of
|
||||
the copyright owner. For the purposes of this definition, "submitted"
|
||||
means any form of electronic, verbal, or written communication sent
|
||||
to the Licensor or its representatives, including but not limited to
|
||||
communication on electronic mailing lists, source code control systems,
|
||||
and issue tracking systems that are managed by, or on behalf of, the
|
||||
Licensor for the purpose of discussing and improving the Work, but
|
||||
excluding communication that is conspicuously marked or otherwise
|
||||
designated in writing by the copyright owner as "Not a Contribution."
|
||||
|
||||
"Contributor" shall mean Licensor and any individual or Legal Entity
|
||||
on behalf of whom a Contribution has been received by Licensor and
|
||||
subsequently incorporated within the Work.
|
||||
|
||||
2. Grant of Copyright License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
copyright license to reproduce, prepare Derivative Works of,
|
||||
publicly display, publicly perform, sublicense, and distribute the
|
||||
Work and such Derivative Works in Source or Object form.
|
||||
|
||||
3. Grant of Patent License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
(except as stated in this section) patent license to make, have made,
|
||||
use, offer to sell, sell, import, and otherwise transfer the Work,
|
||||
where such license applies only to those patent claims licensable
|
||||
by such Contributor that are necessarily infringed by their
|
||||
Contribution(s) alone or by combination of their Contribution(s)
|
||||
with the Work to which such Contribution(s) was submitted. If You
|
||||
institute patent litigation against any entity (including a
|
||||
cross-claim or counterclaim in a lawsuit) alleging that the Work
|
||||
or a Contribution incorporated within the Work constitutes direct
|
||||
or contributory patent infringement, then any patent licenses
|
||||
granted to You under this License for that Work shall terminate
|
||||
as of the date such litigation is filed.
|
||||
|
||||
4. Redistribution. You may reproduce and distribute copies of the
|
||||
Work or Derivative Works thereof in any medium, with or without
|
||||
modifications, and in Source or Object form, provided that You
|
||||
meet the following conditions:
|
||||
|
||||
(a) You must give any other recipients of the Work or
|
||||
Derivative Works a copy of this License; and
|
||||
|
||||
(b) You must cause any modified files to carry prominent notices
|
||||
stating that You changed the files; and
|
||||
|
||||
(c) You must retain, in the Source form of any Derivative Works
|
||||
that You distribute, all copyright, patent, trademark, and
|
||||
attribution notices from the Source form of the Work,
|
||||
excluding those notices that do not pertain to any part of
|
||||
the Derivative Works; and
|
||||
|
||||
(d) If the Work includes a "NOTICE" text file as part of its
|
||||
distribution, then any Derivative Works that You distribute must
|
||||
include a readable copy of the attribution notices contained
|
||||
within such NOTICE file, excluding those notices that do not
|
||||
pertain to any part of the Derivative Works, in at least one
|
||||
of the following places: within a NOTICE text file distributed
|
||||
as part of the Derivative Works; within the Source form or
|
||||
documentation, if provided along with the Derivative Works; or,
|
||||
within a display generated by the Derivative Works, if and
|
||||
wherever such third-party notices normally appear. The contents
|
||||
of the NOTICE file are for informational purposes only and
|
||||
do not modify the License. You may add Your own attribution
|
||||
notices within Derivative Works that You distribute, alongside
|
||||
or as an addendum to the NOTICE text from the Work, provided
|
||||
that such additional attribution notices cannot be construed
|
||||
as modifying the License.
|
||||
|
||||
You may add Your own copyright statement to Your modifications and
|
||||
may provide additional or different license terms and conditions
|
||||
for use, reproduction, or distribution of Your modifications, or
|
||||
for any such Derivative Works as a whole, provided Your use,
|
||||
reproduction, and distribution of the Work otherwise complies with
|
||||
the conditions stated in this License.
|
||||
|
||||
5. Submission of Contributions. Unless You explicitly state otherwise,
|
||||
any Contribution intentionally submitted for inclusion in the Work
|
||||
by You to the Licensor shall be under the terms and conditions of
|
||||
this License, without any additional terms or conditions.
|
||||
Notwithstanding the above, nothing herein shall supersede or modify
|
||||
the terms of any separate license agreement you may have executed
|
||||
with Licensor regarding such Contributions.
|
||||
|
||||
6. Trademarks. This License does not grant permission to use the trade
|
||||
names, trademarks, service marks, or product names of the Licensor,
|
||||
except as required for reasonable and customary use in describing the
|
||||
origin of the Work and reproducing the content of the NOTICE file.
|
||||
|
||||
7. Disclaimer of Warranty. Unless required by applicable law or
|
||||
agreed to in writing, Licensor provides the Work (and each
|
||||
Contributor provides its Contributions) on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
implied, including, without limitation, any warranties or conditions
|
||||
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
|
||||
PARTICULAR PURPOSE. You are solely responsible for determining the
|
||||
appropriateness of using or redistributing the Work and assume any
|
||||
risks associated with Your exercise of permissions under this License.
|
||||
|
||||
8. Limitation of Liability. In no event and under no legal theory,
|
||||
whether in tort (including negligence), contract, or otherwise,
|
||||
unless required by applicable law (such as deliberate and grossly
|
||||
negligent acts) or agreed to in writing, shall any Contributor be
|
||||
liable to You for damages, including any direct, indirect, special,
|
||||
incidental, or consequential damages of any character arising as a
|
||||
result of this License or out of the use or inability to use the
|
||||
Work (including but not limited to damages for loss of goodwill,
|
||||
work stoppage, computer failure or malfunction, or any and all
|
||||
other commercial damages or losses), even if such Contributor
|
||||
has been advised of the possibility of such damages.
|
||||
|
||||
9. Accepting Warranty or Additional Liability. While redistributing
|
||||
the Work or Derivative Works thereof, You may choose to offer,
|
||||
and charge a fee for, acceptance of support, warranty, indemnity,
|
||||
or other liability obligations and/or rights consistent with this
|
||||
License. However, in accepting such obligations, You may act only
|
||||
on Your own behalf and on Your sole responsibility, not on behalf
|
||||
of any other Contributor, and only if You agree to indemnify,
|
||||
defend, and hold each Contributor harmless for any liability
|
||||
incurred by, or claims asserted against, such Contributor by reason
|
||||
of your accepting any such warranty or additional liability.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
|
||||
APPENDIX: How to apply the Apache License to your work.
|
||||
|
||||
To apply the Apache License to your work, attach the following
|
||||
boilerplate notice, with the fields enclosed by brackets "[]"
|
||||
replaced with your own identifying information. (Don't include
|
||||
the brackets!) The text should be enclosed in the appropriate
|
||||
comment syntax for the file format. We also recommend that a
|
||||
file or class name and description of purpose be included on the
|
||||
same "printed page" as the copyright notice for easier
|
||||
identification within third-party archives.
|
||||
|
||||
Copyright [yyyy] [name of copyright owner]
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
@ -0,0 +1,136 @@
|
||||
[//]: # "This README.md file is auto-generated, all changes to this file will be lost."
|
||||
[//]: # "To regenerate it, use `python -m synthtool`."
|
||||
<img src="https://avatars2.githubusercontent.com/u/2810941?v=3&s=96" alt="Google Cloud Platform logo" title="Google Cloud Platform" align="right" height="96" width="96"/>
|
||||
|
||||
# [Google Cloud Common Paginator: Node.js Client](https://github.com/googleapis/nodejs-paginator)
|
||||
|
||||
[](https://cloud.google.com/terms/launch-stages)
|
||||
[](https://www.npmjs.org/package/@google-cloud/paginator)
|
||||
|
||||
|
||||
|
||||
|
||||
A result paging utility used by Google node.js modules
|
||||
|
||||
|
||||
A comprehensive list of changes in each version may be found in
|
||||
[the CHANGELOG](https://github.com/googleapis/nodejs-paginator/blob/main/CHANGELOG.md).
|
||||
|
||||
* [Google Cloud Common Paginator Node.js Client API Reference][client-docs]
|
||||
|
||||
* [github.com/googleapis/nodejs-paginator](https://github.com/googleapis/nodejs-paginator)
|
||||
|
||||
Read more about the client libraries for Cloud APIs, including the older
|
||||
Google APIs Client Libraries, in [Client Libraries Explained][explained].
|
||||
|
||||
[explained]: https://cloud.google.com/apis/docs/client-libraries-explained
|
||||
|
||||
**Table of contents:**
|
||||
|
||||
|
||||
* [Quickstart](#quickstart)
|
||||
|
||||
* [Installing the client library](#installing-the-client-library)
|
||||
* [Using the client library](#using-the-client-library)
|
||||
* [Samples](#samples)
|
||||
* [Versioning](#versioning)
|
||||
* [Contributing](#contributing)
|
||||
* [License](#license)
|
||||
|
||||
## Quickstart
|
||||
|
||||
### Installing the client library
|
||||
|
||||
```bash
|
||||
npm install @google-cloud/paginator
|
||||
```
|
||||
|
||||
|
||||
### Using the client library
|
||||
|
||||
```javascript
|
||||
const {paginator} = require('@google-cloud/paginator');
|
||||
console.log(paginator);
|
||||
|
||||
```
|
||||
|
||||
|
||||
|
||||
## Samples
|
||||
|
||||
Samples are in the [`samples/`](https://github.com/googleapis/nodejs-paginator/tree/main/samples) directory. Each sample's `README.md` has instructions for running its sample.
|
||||
|
||||
| Sample | Source Code | Try it |
|
||||
| --------------------------- | --------------------------------- | ------ |
|
||||
| Quickstart | [source code](https://github.com/googleapis/nodejs-paginator/blob/main/samples/quickstart.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-paginator&page=editor&open_in_editor=samples/quickstart.js,samples/README.md) |
|
||||
| Streamify | [source code](https://github.com/googleapis/nodejs-paginator/blob/main/samples/streamify.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-paginator&page=editor&open_in_editor=samples/streamify.js,samples/README.md) |
|
||||
|
||||
|
||||
|
||||
The [Google Cloud Common Paginator Node.js Client API Reference][client-docs] documentation
|
||||
also contains samples.
|
||||
|
||||
## Supported Node.js Versions
|
||||
|
||||
Our client libraries follow the [Node.js release schedule](https://nodejs.org/en/about/releases/).
|
||||
Libraries are compatible with all current _active_ and _maintenance_ versions of
|
||||
Node.js.
|
||||
If you are using an end-of-life version of Node.js, we recommend that you update
|
||||
as soon as possible to an actively supported LTS version.
|
||||
|
||||
Google's client libraries support legacy versions of Node.js runtimes on a
|
||||
best-efforts basis with the following warnings:
|
||||
|
||||
* Legacy versions are not tested in continuous integration.
|
||||
* Some security patches and features cannot be backported.
|
||||
* Dependencies cannot be kept up-to-date.
|
||||
|
||||
Client libraries targeting some end-of-life versions of Node.js are available, and
|
||||
can be installed through npm [dist-tags](https://docs.npmjs.com/cli/dist-tag).
|
||||
The dist-tags follow the naming convention `legacy-(version)`.
|
||||
For example, `npm install @google-cloud/paginator@legacy-8` installs client libraries
|
||||
for versions compatible with Node.js 8.
|
||||
|
||||
## Versioning
|
||||
|
||||
This library follows [Semantic Versioning](http://semver.org/).
|
||||
|
||||
|
||||
|
||||
This library is considered to be **stable**. The code surface will not change in backwards-incompatible ways
|
||||
unless absolutely necessary (e.g. because of critical security issues) or with
|
||||
an extensive deprecation period. Issues and requests against **stable** libraries
|
||||
are addressed with the highest priority.
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
More Information: [Google Cloud Platform Launch Stages][launch_stages]
|
||||
|
||||
[launch_stages]: https://cloud.google.com/terms/launch-stages
|
||||
|
||||
## Contributing
|
||||
|
||||
Contributions welcome! See the [Contributing Guide](https://github.com/googleapis/nodejs-paginator/blob/main/CONTRIBUTING.md).
|
||||
|
||||
Please note that this `README.md`, the `samples/README.md`,
|
||||
and a variety of configuration files in this repository (including `.nycrc` and `tsconfig.json`)
|
||||
are generated from a central template. To edit one of these files, make an edit
|
||||
to its templates in
|
||||
[directory](https://github.com/googleapis/synthtool).
|
||||
|
||||
## License
|
||||
|
||||
Apache Version 2.0
|
||||
|
||||
See [LICENSE](https://github.com/googleapis/nodejs-paginator/blob/main/LICENSE)
|
||||
|
||||
[client-docs]: https://cloud.google.com/nodejs/docs/reference/paginator/latest
|
||||
|
||||
[shell_img]: https://gstatic.com/cloudssh/images/open-btn.png
|
||||
[projects]: https://console.cloud.google.com/project
|
||||
[billing]: https://support.google.com/cloud/answer/6293499#enable-billing
|
||||
|
||||
[auth]: https://cloud.google.com/docs/authentication/getting-started
|
||||
@ -0,0 +1,131 @@
|
||||
/*!
|
||||
* Copyright 2015 Google Inc. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
/// <reference types="node" />
|
||||
import { TransformOptions } from 'stream';
|
||||
import { ResourceStream } from './resource-stream';
|
||||
export interface ParsedArguments extends TransformOptions {
|
||||
/**
|
||||
* Query object. This is most commonly an object, but to make the API more
|
||||
* simple, it can also be a string in some places.
|
||||
*/
|
||||
query?: ParsedArguments;
|
||||
/**
|
||||
* Callback function.
|
||||
*/
|
||||
callback?: Function;
|
||||
/**
|
||||
* Auto-pagination enabled.
|
||||
*/
|
||||
autoPaginate?: boolean;
|
||||
/**
|
||||
* Maximum API calls to make.
|
||||
*/
|
||||
maxApiCalls?: number;
|
||||
/**
|
||||
* Maximum results to return.
|
||||
*/
|
||||
maxResults?: number;
|
||||
pageSize?: number;
|
||||
streamOptions?: ParsedArguments;
|
||||
}
|
||||
/*! Developer Documentation
|
||||
*
|
||||
* paginator is used to auto-paginate `nextQuery` methods as well as
|
||||
* streamifying them.
|
||||
*
|
||||
* Before:
|
||||
*
|
||||
* search.query('done=true', function(err, results, nextQuery) {
|
||||
* search.query(nextQuery, function(err, results, nextQuery) {});
|
||||
* });
|
||||
*
|
||||
* After:
|
||||
*
|
||||
* search.query('done=true', function(err, results) {});
|
||||
*
|
||||
* Methods to extend should be written to accept callbacks and return a
|
||||
* `nextQuery`.
|
||||
*/
|
||||
export declare class Paginator {
|
||||
/**
|
||||
* Cache the original method, then overwrite it on the Class's prototype.
|
||||
*
|
||||
* @param {function} Class - The parent class of the methods to extend.
|
||||
* @param {string|string[]} methodNames - Name(s) of the methods to extend.
|
||||
*/
|
||||
extend(Class: Function, methodNames: string | string[]): void;
|
||||
/**
|
||||
* Wraps paginated API calls in a readable object stream.
|
||||
*
|
||||
* This method simply calls the nextQuery recursively, emitting results to a
|
||||
* stream. The stream ends when `nextQuery` is null.
|
||||
*
|
||||
* `maxResults` will act as a cap for how many results are fetched and emitted
|
||||
* to the stream.
|
||||
*
|
||||
* @param {string} methodName - Name of the method to streamify.
|
||||
* @return {function} - Wrapped function.
|
||||
*/
|
||||
streamify<T = any>(methodName: string): (this: {
|
||||
[index: string]: Function;
|
||||
}, ...args: any[]) => ResourceStream<T>;
|
||||
/**
|
||||
* Parse a pseudo-array `arguments` for a query and callback.
|
||||
*
|
||||
* @param {array} args - The original `arguments` pseduo-array that the original
|
||||
* method received.
|
||||
*/
|
||||
parseArguments_(args: any[]): ParsedArguments;
|
||||
/**
|
||||
* This simply checks to see if `autoPaginate` is set or not, if it's true
|
||||
* then we buffer all results, otherwise simply call the original method.
|
||||
*
|
||||
* @param {array} parsedArguments - Parsed arguments from the original method
|
||||
* call.
|
||||
* @param {object=|string=} parsedArguments.query - Query object. This is most
|
||||
* commonly an object, but to make the API more simple, it can also be a
|
||||
* string in some places.
|
||||
* @param {function=} parsedArguments.callback - Callback function.
|
||||
* @param {boolean} parsedArguments.autoPaginate - Auto-pagination enabled.
|
||||
* @param {boolean} parsedArguments.maxApiCalls - Maximum API calls to make.
|
||||
* @param {number} parsedArguments.maxResults - Maximum results to return.
|
||||
* @param {function} originalMethod - The cached method that accepts a callback
|
||||
* and returns `nextQuery` to receive more results.
|
||||
*/
|
||||
run_(parsedArguments: ParsedArguments, originalMethod: Function): any;
|
||||
/**
|
||||
* This method simply calls the nextQuery recursively, emitting results to a
|
||||
* stream. The stream ends when `nextQuery` is null.
|
||||
*
|
||||
* `maxResults` will act as a cap for how many results are fetched and emitted
|
||||
* to the stream.
|
||||
*
|
||||
* @param {object=|string=} parsedArguments.query - Query object. This is most
|
||||
* commonly an object, but to make the API more simple, it can also be a
|
||||
* string in some places.
|
||||
* @param {function=} parsedArguments.callback - Callback function.
|
||||
* @param {boolean} parsedArguments.autoPaginate - Auto-pagination enabled.
|
||||
* @param {boolean} parsedArguments.maxApiCalls - Maximum API calls to make.
|
||||
* @param {number} parsedArguments.maxResults - Maximum results to return.
|
||||
* @param {function} originalMethod - The cached method that accepts a callback
|
||||
* and returns `nextQuery` to receive more results.
|
||||
* @return {stream} - Readable object stream.
|
||||
*/
|
||||
runAsStream_<T = any>(parsedArguments: ParsedArguments, originalMethod: Function): ResourceStream<T>;
|
||||
}
|
||||
declare const paginator: Paginator;
|
||||
export { paginator };
|
||||
export { ResourceStream };
|
||||
@ -0,0 +1,206 @@
|
||||
"use strict";
|
||||
/*!
|
||||
* Copyright 2015 Google Inc. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.ResourceStream = exports.paginator = exports.Paginator = void 0;
|
||||
/*!
|
||||
* @module common/paginator
|
||||
*/
|
||||
const arrify = require("arrify");
|
||||
const extend = require("extend");
|
||||
const resource_stream_1 = require("./resource-stream");
|
||||
Object.defineProperty(exports, "ResourceStream", { enumerable: true, get: function () { return resource_stream_1.ResourceStream; } });
|
||||
/*! Developer Documentation
|
||||
*
|
||||
* paginator is used to auto-paginate `nextQuery` methods as well as
|
||||
* streamifying them.
|
||||
*
|
||||
* Before:
|
||||
*
|
||||
* search.query('done=true', function(err, results, nextQuery) {
|
||||
* search.query(nextQuery, function(err, results, nextQuery) {});
|
||||
* });
|
||||
*
|
||||
* After:
|
||||
*
|
||||
* search.query('done=true', function(err, results) {});
|
||||
*
|
||||
* Methods to extend should be written to accept callbacks and return a
|
||||
* `nextQuery`.
|
||||
*/
|
||||
class Paginator {
|
||||
/**
|
||||
* Cache the original method, then overwrite it on the Class's prototype.
|
||||
*
|
||||
* @param {function} Class - The parent class of the methods to extend.
|
||||
* @param {string|string[]} methodNames - Name(s) of the methods to extend.
|
||||
*/
|
||||
// tslint:disable-next-line:variable-name
|
||||
extend(Class, methodNames) {
|
||||
methodNames = arrify(methodNames);
|
||||
methodNames.forEach(methodName => {
|
||||
const originalMethod = Class.prototype[methodName];
|
||||
// map the original method to a private member
|
||||
Class.prototype[methodName + '_'] = originalMethod;
|
||||
// overwrite the original to auto-paginate
|
||||
/* eslint-disable @typescript-eslint/no-explicit-any */
|
||||
Class.prototype[methodName] = function (...args) {
|
||||
const parsedArguments = paginator.parseArguments_(args);
|
||||
return paginator.run_(parsedArguments, originalMethod.bind(this));
|
||||
};
|
||||
});
|
||||
}
|
||||
/**
|
||||
* Wraps paginated API calls in a readable object stream.
|
||||
*
|
||||
* This method simply calls the nextQuery recursively, emitting results to a
|
||||
* stream. The stream ends when `nextQuery` is null.
|
||||
*
|
||||
* `maxResults` will act as a cap for how many results are fetched and emitted
|
||||
* to the stream.
|
||||
*
|
||||
* @param {string} methodName - Name of the method to streamify.
|
||||
* @return {function} - Wrapped function.
|
||||
*/
|
||||
/* eslint-disable @typescript-eslint/no-explicit-any */
|
||||
streamify(methodName) {
|
||||
return function (
|
||||
/* eslint-disable @typescript-eslint/no-explicit-any */
|
||||
...args) {
|
||||
const parsedArguments = paginator.parseArguments_(args);
|
||||
const originalMethod = this[methodName + '_'] || this[methodName];
|
||||
return paginator.runAsStream_(parsedArguments, originalMethod.bind(this));
|
||||
};
|
||||
}
|
||||
/**
|
||||
* Parse a pseudo-array `arguments` for a query and callback.
|
||||
*
|
||||
* @param {array} args - The original `arguments` pseduo-array that the original
|
||||
* method received.
|
||||
*/
|
||||
/* eslint-disable @typescript-eslint/no-explicit-any */
|
||||
parseArguments_(args) {
|
||||
let query;
|
||||
let autoPaginate = true;
|
||||
let maxApiCalls = -1;
|
||||
let maxResults = -1;
|
||||
let callback;
|
||||
const firstArgument = args[0];
|
||||
const lastArgument = args[args.length - 1];
|
||||
if (typeof firstArgument === 'function') {
|
||||
callback = firstArgument;
|
||||
}
|
||||
else {
|
||||
query = firstArgument;
|
||||
}
|
||||
if (typeof lastArgument === 'function') {
|
||||
callback = lastArgument;
|
||||
}
|
||||
if (typeof query === 'object') {
|
||||
query = extend(true, {}, query);
|
||||
// Check if the user only asked for a certain amount of results.
|
||||
if (query.maxResults && typeof query.maxResults === 'number') {
|
||||
// `maxResults` is used API-wide.
|
||||
maxResults = query.maxResults;
|
||||
}
|
||||
else if (typeof query.pageSize === 'number') {
|
||||
// `pageSize` is Pub/Sub's `maxResults`.
|
||||
maxResults = query.pageSize;
|
||||
}
|
||||
if (query.maxApiCalls && typeof query.maxApiCalls === 'number') {
|
||||
maxApiCalls = query.maxApiCalls;
|
||||
delete query.maxApiCalls;
|
||||
}
|
||||
// maxResults is the user specified limit.
|
||||
if (maxResults !== -1 || query.autoPaginate === false) {
|
||||
autoPaginate = false;
|
||||
}
|
||||
}
|
||||
const parsedArguments = {
|
||||
query: query || {},
|
||||
autoPaginate,
|
||||
maxApiCalls,
|
||||
maxResults,
|
||||
callback,
|
||||
};
|
||||
parsedArguments.streamOptions = extend(true, {}, parsedArguments.query);
|
||||
delete parsedArguments.streamOptions.autoPaginate;
|
||||
delete parsedArguments.streamOptions.maxResults;
|
||||
delete parsedArguments.streamOptions.pageSize;
|
||||
return parsedArguments;
|
||||
}
|
||||
/**
|
||||
* This simply checks to see if `autoPaginate` is set or not, if it's true
|
||||
* then we buffer all results, otherwise simply call the original method.
|
||||
*
|
||||
* @param {array} parsedArguments - Parsed arguments from the original method
|
||||
* call.
|
||||
* @param {object=|string=} parsedArguments.query - Query object. This is most
|
||||
* commonly an object, but to make the API more simple, it can also be a
|
||||
* string in some places.
|
||||
* @param {function=} parsedArguments.callback - Callback function.
|
||||
* @param {boolean} parsedArguments.autoPaginate - Auto-pagination enabled.
|
||||
* @param {boolean} parsedArguments.maxApiCalls - Maximum API calls to make.
|
||||
* @param {number} parsedArguments.maxResults - Maximum results to return.
|
||||
* @param {function} originalMethod - The cached method that accepts a callback
|
||||
* and returns `nextQuery` to receive more results.
|
||||
*/
|
||||
run_(parsedArguments, originalMethod) {
|
||||
const query = parsedArguments.query;
|
||||
const callback = parsedArguments.callback;
|
||||
if (!parsedArguments.autoPaginate) {
|
||||
return originalMethod(query, callback);
|
||||
}
|
||||
const results = new Array();
|
||||
const promise = new Promise((resolve, reject) => {
|
||||
paginator
|
||||
.runAsStream_(parsedArguments, originalMethod)
|
||||
.on('error', reject)
|
||||
.on('data', (data) => results.push(data))
|
||||
.on('end', () => resolve(results));
|
||||
});
|
||||
if (!callback) {
|
||||
return promise.then(results => [results]);
|
||||
}
|
||||
promise.then(results => callback(null, results), (err) => callback(err));
|
||||
}
|
||||
/**
|
||||
* This method simply calls the nextQuery recursively, emitting results to a
|
||||
* stream. The stream ends when `nextQuery` is null.
|
||||
*
|
||||
* `maxResults` will act as a cap for how many results are fetched and emitted
|
||||
* to the stream.
|
||||
*
|
||||
* @param {object=|string=} parsedArguments.query - Query object. This is most
|
||||
* commonly an object, but to make the API more simple, it can also be a
|
||||
* string in some places.
|
||||
* @param {function=} parsedArguments.callback - Callback function.
|
||||
* @param {boolean} parsedArguments.autoPaginate - Auto-pagination enabled.
|
||||
* @param {boolean} parsedArguments.maxApiCalls - Maximum API calls to make.
|
||||
* @param {number} parsedArguments.maxResults - Maximum results to return.
|
||||
* @param {function} originalMethod - The cached method that accepts a callback
|
||||
* and returns `nextQuery` to receive more results.
|
||||
* @return {stream} - Readable object stream.
|
||||
*/
|
||||
/* eslint-disable @typescript-eslint/no-explicit-any */
|
||||
runAsStream_(parsedArguments, originalMethod) {
|
||||
return new resource_stream_1.ResourceStream(parsedArguments, originalMethod);
|
||||
}
|
||||
}
|
||||
exports.Paginator = Paginator;
|
||||
const paginator = new Paginator();
|
||||
exports.paginator = paginator;
|
||||
//# sourceMappingURL=index.js.map
|
||||
@ -0,0 +1,40 @@
|
||||
/*!
|
||||
* Copyright 2019 Google Inc. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
/// <reference types="node" />
|
||||
import { Transform, Writable } from 'stream';
|
||||
import { ParsedArguments } from './';
|
||||
interface ResourceEvents<T> {
|
||||
addListener(event: 'data', listener: (data: T) => void): this;
|
||||
emit(event: 'data', data: T): boolean;
|
||||
on(event: 'data', listener: (data: T) => void): this;
|
||||
once(event: 'data', listener: (data: T) => void): this;
|
||||
prependListener(event: 'data', listener: (data: T) => void): this;
|
||||
prependOnceListener(event: 'data', listener: (data: T) => void): this;
|
||||
removeListener(event: 'data', listener: (data: T) => void): this;
|
||||
}
|
||||
export declare class ResourceStream<T> extends Transform implements ResourceEvents<T> {
|
||||
_ended: boolean;
|
||||
_maxApiCalls: number;
|
||||
_nextQuery: {} | null;
|
||||
_reading: boolean;
|
||||
_requestFn: Function;
|
||||
_requestsMade: number;
|
||||
_resultsToSend: number;
|
||||
constructor(args: ParsedArguments, requestFn: Function);
|
||||
end(...args: any[]): ReturnType<Writable['end']> extends Writable ? this : void;
|
||||
_read(): void;
|
||||
}
|
||||
export {};
|
||||
@ -0,0 +1,80 @@
|
||||
"use strict";
|
||||
/*!
|
||||
* Copyright 2019 Google Inc. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.ResourceStream = void 0;
|
||||
const stream_1 = require("stream");
|
||||
class ResourceStream extends stream_1.Transform {
|
||||
constructor(args, requestFn) {
|
||||
const options = Object.assign({ objectMode: true }, args.streamOptions);
|
||||
super(options);
|
||||
this._ended = false;
|
||||
this._maxApiCalls = args.maxApiCalls === -1 ? Infinity : args.maxApiCalls;
|
||||
this._nextQuery = args.query;
|
||||
this._reading = false;
|
||||
this._requestFn = requestFn;
|
||||
this._requestsMade = 0;
|
||||
this._resultsToSend = args.maxResults === -1 ? Infinity : args.maxResults;
|
||||
}
|
||||
/* eslint-disable @typescript-eslint/no-explicit-any */
|
||||
end(...args) {
|
||||
this._ended = true;
|
||||
return super.end(...args);
|
||||
}
|
||||
_read() {
|
||||
if (this._reading) {
|
||||
return;
|
||||
}
|
||||
this._reading = true;
|
||||
// Wrap in a try/catch to catch input linting errors, e.g.
|
||||
// an invalid BigQuery query. These errors are thrown in an
|
||||
// async fashion, which makes them un-catchable by the user.
|
||||
try {
|
||||
this._requestFn(this._nextQuery, (err, results, nextQuery) => {
|
||||
if (err) {
|
||||
this.destroy(err);
|
||||
return;
|
||||
}
|
||||
this._nextQuery = nextQuery;
|
||||
if (this._resultsToSend !== Infinity) {
|
||||
results = results.splice(0, this._resultsToSend);
|
||||
this._resultsToSend -= results.length;
|
||||
}
|
||||
let more = true;
|
||||
for (const result of results) {
|
||||
if (this._ended) {
|
||||
break;
|
||||
}
|
||||
more = this.push(result);
|
||||
}
|
||||
const isFinished = !this._nextQuery || this._resultsToSend < 1;
|
||||
const madeMaxCalls = ++this._requestsMade >= this._maxApiCalls;
|
||||
if (isFinished || madeMaxCalls) {
|
||||
this.end();
|
||||
}
|
||||
if (more && !this._ended) {
|
||||
setImmediate(() => this._read());
|
||||
}
|
||||
this._reading = false;
|
||||
});
|
||||
}
|
||||
catch (e) {
|
||||
this.destroy(e);
|
||||
}
|
||||
}
|
||||
}
|
||||
exports.ResourceStream = ResourceStream;
|
||||
//# sourceMappingURL=resource-stream.js.map
|
||||
@ -0,0 +1,57 @@
|
||||
{
|
||||
"name": "@google-cloud/paginator",
|
||||
"version": "3.0.7",
|
||||
"description": "A result paging utility used by Google node.js modules",
|
||||
"main": "build/src/index.js",
|
||||
"types": "build/src/index.d.ts",
|
||||
"repository": "googleapis/nodejs-paginator",
|
||||
"scripts": {
|
||||
"test": "c8 mocha build/test",
|
||||
"compile": "tsc -p .",
|
||||
"fix": "gts fix",
|
||||
"prelint": "cd samples; npm link ../; npm install",
|
||||
"lint": "gts check",
|
||||
"prepare": "npm run compile",
|
||||
"pretest": "npm run compile",
|
||||
"docs": "compodoc src/",
|
||||
"presystem-test": "npm run compile",
|
||||
"samples-test": "cd samples/ && npm link ../ && npm test && cd ../",
|
||||
"system-test": "mocha build/system-test",
|
||||
"docs-test": "linkinator docs",
|
||||
"predocs-test": "npm run docs",
|
||||
"clean": "gts clean",
|
||||
"precompile": "gts clean"
|
||||
},
|
||||
"keywords": [],
|
||||
"files": [
|
||||
"build/src",
|
||||
"!build/src/**/*.map"
|
||||
],
|
||||
"author": "Google Inc.",
|
||||
"license": "Apache-2.0",
|
||||
"devDependencies": {
|
||||
"@compodoc/compodoc": "^1.1.7",
|
||||
"@types/extend": "^3.0.0",
|
||||
"@types/mocha": "^8.0.0",
|
||||
"@types/node": "^16.0.0",
|
||||
"@types/proxyquire": "^1.3.28",
|
||||
"@types/sinon": "^10.0.0",
|
||||
"@types/uuid": "^8.0.0",
|
||||
"c8": "^7.0.0",
|
||||
"codecov": "^3.0.4",
|
||||
"gts": "^3.0.0",
|
||||
"linkinator": "^2.0.0",
|
||||
"mocha": "^8.0.0",
|
||||
"proxyquire": "^2.0.1",
|
||||
"sinon": "^13.0.0",
|
||||
"typescript": "^3.8.3",
|
||||
"uuid": "^8.0.0"
|
||||
},
|
||||
"dependencies": {
|
||||
"arrify": "^2.0.0",
|
||||
"extend": "^3.0.2"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=10"
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,180 @@
|
||||
# Changelog
|
||||
|
||||
[npm history][1]
|
||||
|
||||
[1]: https://www.npmjs.com/package/@google-cloud/projectify?activeTab=versions
|
||||
## [3.0.0](https://github.com/googleapis/nodejs-projectify/compare/v2.1.1...v3.0.0) (2022-05-20)
|
||||
|
||||
|
||||
### ⚠ BREAKING CHANGES
|
||||
|
||||
* update library to use Node 12 (#299)
|
||||
|
||||
### Build System
|
||||
|
||||
* update library to use Node 12 ([#299](https://github.com/googleapis/nodejs-projectify/issues/299)) ([83b63ca](https://github.com/googleapis/nodejs-projectify/commit/83b63ca8cb89086a8535a9fc8abd39e95f0cecd4))
|
||||
|
||||
### [2.1.1](https://www.github.com/googleapis/nodejs-projectify/compare/v2.1.0...v2.1.1) (2021-09-09)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **build:** switch primary branch to main ([#267](https://www.github.com/googleapis/nodejs-projectify/issues/267)) ([9e8d6e4](https://www.github.com/googleapis/nodejs-projectify/commit/9e8d6e48c080806b42164d7be0bd11197996f245))
|
||||
|
||||
## [2.1.0](https://www.github.com/googleapis/nodejs-projectify/compare/v2.0.1...v2.1.0) (2021-06-10)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* add `gcf-owl-bot[bot]` to `ignoreAuthors` ([#245](https://www.github.com/googleapis/nodejs-projectify/issues/245)) ([30f0499](https://www.github.com/googleapis/nodejs-projectify/commit/30f0499ade5f140774c3aa672b44fd3538e72309))
|
||||
|
||||
### [2.0.1](https://www.github.com/googleapis/nodejs-projectify/compare/v2.0.0...v2.0.1) (2020-07-06)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* update node issue template ([#197](https://www.github.com/googleapis/nodejs-projectify/issues/197)) ([3406f2a](https://www.github.com/googleapis/nodejs-projectify/commit/3406f2aa431ed04541585b63c330c04270c602aa))
|
||||
|
||||
## [2.0.0](https://www.github.com/googleapis/nodejs-projectify/compare/v1.0.4...v2.0.0) (2020-03-24)
|
||||
|
||||
|
||||
### ⚠ BREAKING CHANGES
|
||||
|
||||
* typescript@3.7 introduced some breaking changes
|
||||
* drop Node 8 from engines field (#172)
|
||||
|
||||
### Features
|
||||
|
||||
* drop Node 8 from engines field ([#172](https://www.github.com/googleapis/nodejs-projectify/issues/172)) ([3eac424](https://www.github.com/googleapis/nodejs-projectify/commit/3eac424bfb1ee47144a77888dc68db687988945e))
|
||||
|
||||
|
||||
### Build System
|
||||
|
||||
* update to latest version of gts/typescript ([#171](https://www.github.com/googleapis/nodejs-projectify/issues/171)) ([30f90cc](https://www.github.com/googleapis/nodejs-projectify/commit/30f90cc172da6ed9394da91869556bf5eef42434))
|
||||
|
||||
### [1.0.4](https://www.github.com/googleapis/nodejs-projectify/compare/v1.0.3...v1.0.4) (2019-12-05)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **publish:** publication failed to reach npm ([#141](https://www.github.com/googleapis/nodejs-projectify/issues/141)) ([5406ba5](https://www.github.com/googleapis/nodejs-projectify/commit/5406ba5e1d43a228a19072023c1baebce34190af))
|
||||
|
||||
### [1.0.3](https://www.github.com/googleapis/nodejs-projectify/compare/v1.0.2...v1.0.3) (2019-12-05)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **deps:** pin TypeScript below 3.7.0 ([6c95307](https://www.github.com/googleapis/nodejs-projectify/commit/6c953070139a77d30c4ce5b7dee1443874046906))
|
||||
|
||||
### [1.0.2](https://www.github.com/googleapis/nodejs-projectify/compare/v1.0.1...v1.0.2) (2019-11-14)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **docs:** add jsdoc-region-tag plugin ([#135](https://www.github.com/googleapis/nodejs-projectify/issues/135)) ([59301e7](https://www.github.com/googleapis/nodejs-projectify/commit/59301e7cfa855add4894dd9c46870e61fffa7413))
|
||||
|
||||
### [1.0.1](https://www.github.com/googleapis/nodejs-projectify/compare/v1.0.0...v1.0.1) (2019-06-26)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **docs:** link to reference docs section on googleapis.dev ([#119](https://www.github.com/googleapis/nodejs-projectify/issues/119)) ([90a009f](https://www.github.com/googleapis/nodejs-projectify/commit/90a009f))
|
||||
|
||||
## [1.0.0](https://www.github.com/googleapis/nodejs-projectify/compare/v0.3.3...v1.0.0) (2019-05-02)
|
||||
|
||||
|
||||
### Build System
|
||||
|
||||
* upgrade engines field to >=8.10.0 ([#103](https://www.github.com/googleapis/nodejs-projectify/issues/103)) ([0149650](https://www.github.com/googleapis/nodejs-projectify/commit/0149650))
|
||||
|
||||
|
||||
### BREAKING CHANGES
|
||||
|
||||
* upgrade engines field to >=8.10.0 (#103)
|
||||
|
||||
## v0.3.3
|
||||
|
||||
03-12-2019 12:27 PDT
|
||||
|
||||
This patch release contains a few updates to the docs. That's all!
|
||||
|
||||
### Documentation
|
||||
- docs: update links in contrib guide ([#86](https://github.com/googleapis/nodejs-projectify/pull/86))
|
||||
- docs: update contributing path in README ([#82](https://github.com/googleapis/nodejs-projectify/pull/82))
|
||||
- docs: move CONTRIBUTING.md to root ([#81](https://github.com/googleapis/nodejs-projectify/pull/81))
|
||||
- docs: add lint/fix example to contributing guide ([#79](https://github.com/googleapis/nodejs-projectify/pull/79))
|
||||
|
||||
### Internal / Testing Changes
|
||||
- build: Add docuploader credentials to node publish jobs ([#90](https://github.com/googleapis/nodejs-projectify/pull/90))
|
||||
- build: use node10 to run samples-test, system-test etc ([#89](https://github.com/googleapis/nodejs-projectify/pull/89))
|
||||
- build: update release configuration
|
||||
- chore(deps): update dependency mocha to v6
|
||||
- build: use linkinator for docs test ([#85](https://github.com/googleapis/nodejs-projectify/pull/85))
|
||||
- build: create docs test npm scripts ([#84](https://github.com/googleapis/nodejs-projectify/pull/84))
|
||||
- build: test using @grpc/grpc-js in CI ([#83](https://github.com/googleapis/nodejs-projectify/pull/83))
|
||||
- build: ignore googleapis.com in doc link check ([#78](https://github.com/googleapis/nodejs-projectify/pull/78))
|
||||
- build: check for 404s in the docs ([#77](https://github.com/googleapis/nodejs-projectify/pull/77))
|
||||
- chore(build): inject yoshi automation key ([#75](https://github.com/googleapis/nodejs-projectify/pull/75))
|
||||
- chore: update nyc and eslint configs ([#74](https://github.com/googleapis/nodejs-projectify/pull/74))
|
||||
- chore: fix publish.sh permission +x ([#72](https://github.com/googleapis/nodejs-projectify/pull/72))
|
||||
- fix(build): fix Kokoro release script ([#71](https://github.com/googleapis/nodejs-projectify/pull/71))
|
||||
- build: add Kokoro configs for autorelease ([#70](https://github.com/googleapis/nodejs-projectify/pull/70))
|
||||
- chore: always nyc report before calling codecov ([#67](https://github.com/googleapis/nodejs-projectify/pull/67))
|
||||
- chore: nyc ignore build/test by default ([#66](https://github.com/googleapis/nodejs-projectify/pull/66))
|
||||
- chore(build): update prettier config ([#64](https://github.com/googleapis/nodejs-projectify/pull/64))
|
||||
- chore: update license file ([#63](https://github.com/googleapis/nodejs-projectify/pull/63))
|
||||
- fix(build): fix system key decryption ([#59](https://github.com/googleapis/nodejs-projectify/pull/59))
|
||||
- chore: add synth.metadata
|
||||
|
||||
## v0.3.2
|
||||
|
||||
### Bug fixes
|
||||
- fix: do not replace projectId on stream objects ([#53](https://github.com/googleapis/nodejs-projectify/pull/53))
|
||||
|
||||
### Dependencies
|
||||
- chore(deps): update dependency gts to ^0.9.0 ([#52](https://github.com/googleapis/nodejs-projectify/pull/52))
|
||||
|
||||
### Internal / Testing Changes
|
||||
- chore: update eslintignore config ([#51](https://github.com/googleapis/nodejs-projectify/pull/51))
|
||||
- chore: use latest npm on Windows ([#50](https://github.com/googleapis/nodejs-projectify/pull/50))
|
||||
- chore: update CircleCI config ([#49](https://github.com/googleapis/nodejs-projectify/pull/49))
|
||||
- chore: include build in eslintignore ([#46](https://github.com/googleapis/nodejs-projectify/pull/46))
|
||||
|
||||
## v0.3.1
|
||||
|
||||
### Implementation Changes
|
||||
- fix: replaceProjectId should not fail when passed a Buffer ([#43](https://github.com/googleapis/nodejs-projectify/pull/43))
|
||||
|
||||
### Dependencies
|
||||
- chore(deps): update dependency nyc to v13 ([#13](https://github.com/googleapis/nodejs-projectify/pull/13))
|
||||
- chore(deps): lock file maintenance ([#11](https://github.com/googleapis/nodejs-projectify/pull/11))
|
||||
- chore(deps): lock file maintenance ([#8](https://github.com/googleapis/nodejs-projectify/pull/8))
|
||||
- chore(deps): update dependency typescript to v3 ([#7](https://github.com/googleapis/nodejs-projectify/pull/7))
|
||||
- chore(deps): update dependency gts to ^0.8.0 ([#2](https://github.com/googleapis/nodejs-projectify/pull/2))
|
||||
- chore(deps): lock file maintenance ([#4](https://github.com/googleapis/nodejs-projectify/pull/4))
|
||||
- chore(deps): lock file maintenance ([#3](https://github.com/googleapis/nodejs-projectify/pull/3))
|
||||
|
||||
### Internal / Testing Changes
|
||||
- chore: update issue templates ([#40](https://github.com/googleapis/nodejs-projectify/pull/40))
|
||||
- chore: remove old issue template ([#38](https://github.com/googleapis/nodejs-projectify/pull/38))
|
||||
- build: run tests on node11 ([#37](https://github.com/googleapis/nodejs-projectify/pull/37))
|
||||
- chores(build): run codecov on continuous builds ([#34](https://github.com/googleapis/nodejs-projectify/pull/34))
|
||||
- chores(build): do not collect sponge.xml from windows builds ([#35](https://github.com/googleapis/nodejs-projectify/pull/35))
|
||||
- chore: update new issue template ([#33](https://github.com/googleapis/nodejs-projectify/pull/33))
|
||||
- build: fix codecov uploading on Kokoro ([#30](https://github.com/googleapis/nodejs-projectify/pull/30))
|
||||
- Update kokoro config ([#28](https://github.com/googleapis/nodejs-projectify/pull/28))
|
||||
- Update CI config ([#26](https://github.com/googleapis/nodejs-projectify/pull/26))
|
||||
- Don't publish sourcemaps ([#24](https://github.com/googleapis/nodejs-projectify/pull/24))
|
||||
- build: prevent system/sample-test from leaking credentials
|
||||
- Update kokoro config ([#22](https://github.com/googleapis/nodejs-projectify/pull/22))
|
||||
- test: remove appveyor config ([#21](https://github.com/googleapis/nodejs-projectify/pull/21))
|
||||
- Update CI config ([#20](https://github.com/googleapis/nodejs-projectify/pull/20))
|
||||
- Enable prefer-const in the eslint config ([#19](https://github.com/googleapis/nodejs-projectify/pull/19))
|
||||
- Enable no-var in eslint ([#18](https://github.com/googleapis/nodejs-projectify/pull/18))
|
||||
- Update CI config ([#17](https://github.com/googleapis/nodejs-projectify/pull/17))
|
||||
- Add synth and update CI config ([#15](https://github.com/googleapis/nodejs-projectify/pull/15))
|
||||
- chore: ignore package-lock.json ([#12](https://github.com/googleapis/nodejs-projectify/pull/12))
|
||||
- chore: update renovate config ([#10](https://github.com/googleapis/nodejs-projectify/pull/10))
|
||||
- remove that whitespace ([#9](https://github.com/googleapis/nodejs-projectify/pull/9))
|
||||
- chore: assert.deelEqual => assert.deepStrictEqual ([#6](https://github.com/googleapis/nodejs-projectify/pull/6))
|
||||
- chore: move mocha options to mocha.opts ([#5](https://github.com/googleapis/nodejs-projectify/pull/5))
|
||||
@ -0,0 +1,202 @@
|
||||
|
||||
Apache License
|
||||
Version 2.0, January 2004
|
||||
http://www.apache.org/licenses/
|
||||
|
||||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||
|
||||
1. Definitions.
|
||||
|
||||
"License" shall mean the terms and conditions for use, reproduction,
|
||||
and distribution as defined by Sections 1 through 9 of this document.
|
||||
|
||||
"Licensor" shall mean the copyright owner or entity authorized by
|
||||
the copyright owner that is granting the License.
|
||||
|
||||
"Legal Entity" shall mean the union of the acting entity and all
|
||||
other entities that control, are controlled by, or are under common
|
||||
control with that entity. For the purposes of this definition,
|
||||
"control" means (i) the power, direct or indirect, to cause the
|
||||
direction or management of such entity, whether by contract or
|
||||
otherwise, or (ii) ownership of fifty percent (50%) or more of the
|
||||
outstanding shares, or (iii) beneficial ownership of such entity.
|
||||
|
||||
"You" (or "Your") shall mean an individual or Legal Entity
|
||||
exercising permissions granted by this License.
|
||||
|
||||
"Source" form shall mean the preferred form for making modifications,
|
||||
including but not limited to software source code, documentation
|
||||
source, and configuration files.
|
||||
|
||||
"Object" form shall mean any form resulting from mechanical
|
||||
transformation or translation of a Source form, including but
|
||||
not limited to compiled object code, generated documentation,
|
||||
and conversions to other media types.
|
||||
|
||||
"Work" shall mean the work of authorship, whether in Source or
|
||||
Object form, made available under the License, as indicated by a
|
||||
copyright notice that is included in or attached to the work
|
||||
(an example is provided in the Appendix below).
|
||||
|
||||
"Derivative Works" shall mean any work, whether in Source or Object
|
||||
form, that is based on (or derived from) the Work and for which the
|
||||
editorial revisions, annotations, elaborations, or other modifications
|
||||
represent, as a whole, an original work of authorship. For the purposes
|
||||
of this License, Derivative Works shall not include works that remain
|
||||
separable from, or merely link (or bind by name) to the interfaces of,
|
||||
the Work and Derivative Works thereof.
|
||||
|
||||
"Contribution" shall mean any work of authorship, including
|
||||
the original version of the Work and any modifications or additions
|
||||
to that Work or Derivative Works thereof, that is intentionally
|
||||
submitted to Licensor for inclusion in the Work by the copyright owner
|
||||
or by an individual or Legal Entity authorized to submit on behalf of
|
||||
the copyright owner. For the purposes of this definition, "submitted"
|
||||
means any form of electronic, verbal, or written communication sent
|
||||
to the Licensor or its representatives, including but not limited to
|
||||
communication on electronic mailing lists, source code control systems,
|
||||
and issue tracking systems that are managed by, or on behalf of, the
|
||||
Licensor for the purpose of discussing and improving the Work, but
|
||||
excluding communication that is conspicuously marked or otherwise
|
||||
designated in writing by the copyright owner as "Not a Contribution."
|
||||
|
||||
"Contributor" shall mean Licensor and any individual or Legal Entity
|
||||
on behalf of whom a Contribution has been received by Licensor and
|
||||
subsequently incorporated within the Work.
|
||||
|
||||
2. Grant of Copyright License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
copyright license to reproduce, prepare Derivative Works of,
|
||||
publicly display, publicly perform, sublicense, and distribute the
|
||||
Work and such Derivative Works in Source or Object form.
|
||||
|
||||
3. Grant of Patent License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
(except as stated in this section) patent license to make, have made,
|
||||
use, offer to sell, sell, import, and otherwise transfer the Work,
|
||||
where such license applies only to those patent claims licensable
|
||||
by such Contributor that are necessarily infringed by their
|
||||
Contribution(s) alone or by combination of their Contribution(s)
|
||||
with the Work to which such Contribution(s) was submitted. If You
|
||||
institute patent litigation against any entity (including a
|
||||
cross-claim or counterclaim in a lawsuit) alleging that the Work
|
||||
or a Contribution incorporated within the Work constitutes direct
|
||||
or contributory patent infringement, then any patent licenses
|
||||
granted to You under this License for that Work shall terminate
|
||||
as of the date such litigation is filed.
|
||||
|
||||
4. Redistribution. You may reproduce and distribute copies of the
|
||||
Work or Derivative Works thereof in any medium, with or without
|
||||
modifications, and in Source or Object form, provided that You
|
||||
meet the following conditions:
|
||||
|
||||
(a) You must give any other recipients of the Work or
|
||||
Derivative Works a copy of this License; and
|
||||
|
||||
(b) You must cause any modified files to carry prominent notices
|
||||
stating that You changed the files; and
|
||||
|
||||
(c) You must retain, in the Source form of any Derivative Works
|
||||
that You distribute, all copyright, patent, trademark, and
|
||||
attribution notices from the Source form of the Work,
|
||||
excluding those notices that do not pertain to any part of
|
||||
the Derivative Works; and
|
||||
|
||||
(d) If the Work includes a "NOTICE" text file as part of its
|
||||
distribution, then any Derivative Works that You distribute must
|
||||
include a readable copy of the attribution notices contained
|
||||
within such NOTICE file, excluding those notices that do not
|
||||
pertain to any part of the Derivative Works, in at least one
|
||||
of the following places: within a NOTICE text file distributed
|
||||
as part of the Derivative Works; within the Source form or
|
||||
documentation, if provided along with the Derivative Works; or,
|
||||
within a display generated by the Derivative Works, if and
|
||||
wherever such third-party notices normally appear. The contents
|
||||
of the NOTICE file are for informational purposes only and
|
||||
do not modify the License. You may add Your own attribution
|
||||
notices within Derivative Works that You distribute, alongside
|
||||
or as an addendum to the NOTICE text from the Work, provided
|
||||
that such additional attribution notices cannot be construed
|
||||
as modifying the License.
|
||||
|
||||
You may add Your own copyright statement to Your modifications and
|
||||
may provide additional or different license terms and conditions
|
||||
for use, reproduction, or distribution of Your modifications, or
|
||||
for any such Derivative Works as a whole, provided Your use,
|
||||
reproduction, and distribution of the Work otherwise complies with
|
||||
the conditions stated in this License.
|
||||
|
||||
5. Submission of Contributions. Unless You explicitly state otherwise,
|
||||
any Contribution intentionally submitted for inclusion in the Work
|
||||
by You to the Licensor shall be under the terms and conditions of
|
||||
this License, without any additional terms or conditions.
|
||||
Notwithstanding the above, nothing herein shall supersede or modify
|
||||
the terms of any separate license agreement you may have executed
|
||||
with Licensor regarding such Contributions.
|
||||
|
||||
6. Trademarks. This License does not grant permission to use the trade
|
||||
names, trademarks, service marks, or product names of the Licensor,
|
||||
except as required for reasonable and customary use in describing the
|
||||
origin of the Work and reproducing the content of the NOTICE file.
|
||||
|
||||
7. Disclaimer of Warranty. Unless required by applicable law or
|
||||
agreed to in writing, Licensor provides the Work (and each
|
||||
Contributor provides its Contributions) on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
implied, including, without limitation, any warranties or conditions
|
||||
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
|
||||
PARTICULAR PURPOSE. You are solely responsible for determining the
|
||||
appropriateness of using or redistributing the Work and assume any
|
||||
risks associated with Your exercise of permissions under this License.
|
||||
|
||||
8. Limitation of Liability. In no event and under no legal theory,
|
||||
whether in tort (including negligence), contract, or otherwise,
|
||||
unless required by applicable law (such as deliberate and grossly
|
||||
negligent acts) or agreed to in writing, shall any Contributor be
|
||||
liable to You for damages, including any direct, indirect, special,
|
||||
incidental, or consequential damages of any character arising as a
|
||||
result of this License or out of the use or inability to use the
|
||||
Work (including but not limited to damages for loss of goodwill,
|
||||
work stoppage, computer failure or malfunction, or any and all
|
||||
other commercial damages or losses), even if such Contributor
|
||||
has been advised of the possibility of such damages.
|
||||
|
||||
9. Accepting Warranty or Additional Liability. While redistributing
|
||||
the Work or Derivative Works thereof, You may choose to offer,
|
||||
and charge a fee for, acceptance of support, warranty, indemnity,
|
||||
or other liability obligations and/or rights consistent with this
|
||||
License. However, in accepting such obligations, You may act only
|
||||
on Your own behalf and on Your sole responsibility, not on behalf
|
||||
of any other Contributor, and only if You agree to indemnify,
|
||||
defend, and hold each Contributor harmless for any liability
|
||||
incurred by, or claims asserted against, such Contributor by reason
|
||||
of your accepting any such warranty or additional liability.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
|
||||
APPENDIX: How to apply the Apache License to your work.
|
||||
|
||||
To apply the Apache License to your work, attach the following
|
||||
boilerplate notice, with the fields enclosed by brackets "[]"
|
||||
replaced with your own identifying information. (Don't include
|
||||
the brackets!) The text should be enclosed in the appropriate
|
||||
comment syntax for the file format. We also recommend that a
|
||||
file or class name and description of purpose be included on the
|
||||
same "printed page" as the copyright notice for easier
|
||||
identification within third-party archives.
|
||||
|
||||
Copyright [yyyy] [name of copyright owner]
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
@ -0,0 +1,138 @@
|
||||
[//]: # "This README.md file is auto-generated, all changes to this file will be lost."
|
||||
[//]: # "To regenerate it, use `python -m synthtool`."
|
||||
<img src="https://avatars2.githubusercontent.com/u/2810941?v=3&s=96" alt="Google Cloud Platform logo" title="Google Cloud Platform" align="right" height="96" width="96"/>
|
||||
|
||||
# [Google Cloud Common Projectify: Node.js Client](https://github.com/googleapis/nodejs-projectify)
|
||||
|
||||
[](https://cloud.google.com/terms/launch-stages)
|
||||
[](https://www.npmjs.org/package/@google-cloud/projectify)
|
||||
|
||||
|
||||
|
||||
|
||||
A simple utility for replacing the projectid token in objects.
|
||||
|
||||
|
||||
A comprehensive list of changes in each version may be found in
|
||||
[the CHANGELOG](https://github.com/googleapis/nodejs-projectify/blob/main/CHANGELOG.md).
|
||||
|
||||
* [Google Cloud Common Projectify Node.js Client API Reference][client-docs]
|
||||
|
||||
* [github.com/googleapis/nodejs-projectify](https://github.com/googleapis/nodejs-projectify)
|
||||
|
||||
Read more about the client libraries for Cloud APIs, including the older
|
||||
Google APIs Client Libraries, in [Client Libraries Explained][explained].
|
||||
|
||||
[explained]: https://cloud.google.com/apis/docs/client-libraries-explained
|
||||
|
||||
**Table of contents:**
|
||||
|
||||
|
||||
* [Quickstart](#quickstart)
|
||||
|
||||
* [Installing the client library](#installing-the-client-library)
|
||||
* [Using the client library](#using-the-client-library)
|
||||
* [Samples](#samples)
|
||||
* [Versioning](#versioning)
|
||||
* [Contributing](#contributing)
|
||||
* [License](#license)
|
||||
|
||||
## Quickstart
|
||||
|
||||
### Installing the client library
|
||||
|
||||
```bash
|
||||
npm install @google-cloud/projectify
|
||||
```
|
||||
|
||||
|
||||
### Using the client library
|
||||
|
||||
```javascript
|
||||
const {replaceProjectIdToken} = require('@google-cloud/projectify');
|
||||
const options = {
|
||||
projectId: '{{projectId}}',
|
||||
};
|
||||
replaceProjectIdToken(options, 'fake-project-id');
|
||||
|
||||
```
|
||||
|
||||
|
||||
|
||||
## Samples
|
||||
|
||||
Samples are in the [`samples/`](https://github.com/googleapis/nodejs-projectify/tree/main/samples) directory. Each sample's `README.md` has instructions for running its sample.
|
||||
|
||||
| Sample | Source Code | Try it |
|
||||
| --------------------------- | --------------------------------- | ------ |
|
||||
| Quickstart | [source code](https://github.com/googleapis/nodejs-projectify/blob/main/samples/quickstart.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-projectify&page=editor&open_in_editor=samples/quickstart.js,samples/README.md) |
|
||||
|
||||
|
||||
|
||||
The [Google Cloud Common Projectify Node.js Client API Reference][client-docs] documentation
|
||||
also contains samples.
|
||||
|
||||
## Supported Node.js Versions
|
||||
|
||||
Our client libraries follow the [Node.js release schedule](https://nodejs.org/en/about/releases/).
|
||||
Libraries are compatible with all current _active_ and _maintenance_ versions of
|
||||
Node.js.
|
||||
If you are using an end-of-life version of Node.js, we recommend that you update
|
||||
as soon as possible to an actively supported LTS version.
|
||||
|
||||
Google's client libraries support legacy versions of Node.js runtimes on a
|
||||
best-efforts basis with the following warnings:
|
||||
|
||||
* Legacy versions are not tested in continuous integration.
|
||||
* Some security patches and features cannot be backported.
|
||||
* Dependencies cannot be kept up-to-date.
|
||||
|
||||
Client libraries targeting some end-of-life versions of Node.js are available, and
|
||||
can be installed through npm [dist-tags](https://docs.npmjs.com/cli/dist-tag).
|
||||
The dist-tags follow the naming convention `legacy-(version)`.
|
||||
For example, `npm install @google-cloud/projectify@legacy-8` installs client libraries
|
||||
for versions compatible with Node.js 8.
|
||||
|
||||
## Versioning
|
||||
|
||||
This library follows [Semantic Versioning](http://semver.org/).
|
||||
|
||||
|
||||
|
||||
This library is considered to be **stable**. The code surface will not change in backwards-incompatible ways
|
||||
unless absolutely necessary (e.g. because of critical security issues) or with
|
||||
an extensive deprecation period. Issues and requests against **stable** libraries
|
||||
are addressed with the highest priority.
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
More Information: [Google Cloud Platform Launch Stages][launch_stages]
|
||||
|
||||
[launch_stages]: https://cloud.google.com/terms/launch-stages
|
||||
|
||||
## Contributing
|
||||
|
||||
Contributions welcome! See the [Contributing Guide](https://github.com/googleapis/nodejs-projectify/blob/main/CONTRIBUTING.md).
|
||||
|
||||
Please note that this `README.md`, the `samples/README.md`,
|
||||
and a variety of configuration files in this repository (including `.nycrc` and `tsconfig.json`)
|
||||
are generated from a central template. To edit one of these files, make an edit
|
||||
to its templates in
|
||||
[directory](https://github.com/googleapis/synthtool).
|
||||
|
||||
## License
|
||||
|
||||
Apache Version 2.0
|
||||
|
||||
See [LICENSE](https://github.com/googleapis/nodejs-projectify/blob/main/LICENSE)
|
||||
|
||||
[client-docs]: https://cloud.google.com/nodejs/docs/reference/projectify/latest
|
||||
|
||||
[shell_img]: https://gstatic.com/cloudssh/images/open-btn.png
|
||||
[projects]: https://console.cloud.google.com/project
|
||||
[billing]: https://support.google.com/cloud/answer/6293499#enable-billing
|
||||
|
||||
[auth]: https://cloud.google.com/docs/authentication/getting-started
|
||||
@ -0,0 +1,16 @@
|
||||
/**
|
||||
* Populate the `{{projectId}}` placeholder.
|
||||
*
|
||||
* @throws {Error} If a projectId is required, but one is not provided.
|
||||
*
|
||||
* @param {*} - Any input value that may contain a placeholder. Arrays and objects will be looped.
|
||||
* @param {string} projectId - A projectId. If not provided
|
||||
* @return {*} - The original argument with all placeholders populated.
|
||||
*/
|
||||
export declare function replaceProjectIdToken(value: any, projectId: string): any;
|
||||
/**
|
||||
* Custom error type for missing project ID errors.
|
||||
*/
|
||||
export declare class MissingProjectIdError extends Error {
|
||||
message: string;
|
||||
}
|
||||
@ -0,0 +1,66 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.MissingProjectIdError = exports.replaceProjectIdToken = void 0;
|
||||
const stream_1 = require("stream");
|
||||
// Copyright 2014 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
/**
|
||||
* Populate the `{{projectId}}` placeholder.
|
||||
*
|
||||
* @throws {Error} If a projectId is required, but one is not provided.
|
||||
*
|
||||
* @param {*} - Any input value that may contain a placeholder. Arrays and objects will be looped.
|
||||
* @param {string} projectId - A projectId. If not provided
|
||||
* @return {*} - The original argument with all placeholders populated.
|
||||
*/
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
function replaceProjectIdToken(value, projectId) {
|
||||
if (Array.isArray(value)) {
|
||||
value = value.map(v => replaceProjectIdToken(v, projectId));
|
||||
}
|
||||
if (value !== null &&
|
||||
typeof value === 'object' &&
|
||||
!(value instanceof Buffer) &&
|
||||
!(value instanceof stream_1.Stream) &&
|
||||
typeof value.hasOwnProperty === 'function') {
|
||||
for (const opt in value) {
|
||||
// eslint-disable-next-line no-prototype-builtins
|
||||
if (value.hasOwnProperty(opt)) {
|
||||
value[opt] = replaceProjectIdToken(value[opt], projectId);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (typeof value === 'string' &&
|
||||
value.indexOf('{{projectId}}') > -1) {
|
||||
if (!projectId || projectId === '{{projectId}}') {
|
||||
throw new MissingProjectIdError();
|
||||
}
|
||||
value = value.replace(/{{projectId}}/g, projectId);
|
||||
}
|
||||
return value;
|
||||
}
|
||||
exports.replaceProjectIdToken = replaceProjectIdToken;
|
||||
/**
|
||||
* Custom error type for missing project ID errors.
|
||||
*/
|
||||
class MissingProjectIdError extends Error {
|
||||
constructor() {
|
||||
super(...arguments);
|
||||
this.message = `Sorry, we cannot connect to Cloud Services without a project
|
||||
ID. You may specify one with an environment variable named
|
||||
"GOOGLE_CLOUD_PROJECT".`.replace(/ +/g, ' ');
|
||||
}
|
||||
}
|
||||
exports.MissingProjectIdError = MissingProjectIdError;
|
||||
//# sourceMappingURL=index.js.map
|
||||
@ -0,0 +1,46 @@
|
||||
{
|
||||
"name": "@google-cloud/projectify",
|
||||
"version": "3.0.0",
|
||||
"description": "A simple utility for replacing the projectid token in objects.",
|
||||
"main": "build/src/index.js",
|
||||
"types": "build/src/index.d.ts",
|
||||
"repository": "googleapis/nodejs-projectify",
|
||||
"scripts": {
|
||||
"test": "c8 mocha build/test",
|
||||
"lint": "gts check",
|
||||
"clean": "gts clean",
|
||||
"compile": "tsc -p .",
|
||||
"fix": "gts fix",
|
||||
"prepare": "npm run compile",
|
||||
"pretest": "npm run compile",
|
||||
"docs": "compodoc src/",
|
||||
"presystem-test": "npm run compile",
|
||||
"samples-test": "cd samples/ && npm link ../ && npm test && cd ../",
|
||||
"system-test": "mocha build/system-test",
|
||||
"docs-test": "linkinator docs",
|
||||
"predocs-test": "npm run docs",
|
||||
"prelint": "cd samples; npm link ../; npm install",
|
||||
"precompile": "gts clean"
|
||||
},
|
||||
"keywords": [],
|
||||
"files": [
|
||||
"build/src",
|
||||
"!build/src/**/*.map"
|
||||
],
|
||||
"author": "Google Inc.",
|
||||
"license": "Apache-2.0",
|
||||
"devDependencies": {
|
||||
"@compodoc/compodoc": "^1.1.11",
|
||||
"@types/mocha": "^9.0.0",
|
||||
"@types/node": "^16.0.0",
|
||||
"c8": "^7.1.0",
|
||||
"codecov": "^3.6.5",
|
||||
"gts": "^3.1.0",
|
||||
"linkinator": "^2.0.4",
|
||||
"mocha": "^9.2.2",
|
||||
"typescript": "^4.6.4"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12.0.0"
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,180 @@
|
||||
# Changelog
|
||||
|
||||
[npm history][1]
|
||||
|
||||
[1]: https://www.npmjs.com/package/nodejs-promisify?activeTab=versions
|
||||
|
||||
## [3.0.1](https://github.com/googleapis/nodejs-promisify/compare/v3.0.0...v3.0.1) (2022-08-23)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* remove pip install statements ([#1546](https://github.com/googleapis/nodejs-promisify/issues/1546)) ([#310](https://github.com/googleapis/nodejs-promisify/issues/310)) ([c7c6883](https://github.com/googleapis/nodejs-promisify/commit/c7c688389de72ddc0181b19bceee2d95eacd3d96))
|
||||
|
||||
## [3.0.0](https://github.com/googleapis/nodejs-promisify/compare/v2.0.4...v3.0.0) (2022-05-03)
|
||||
|
||||
|
||||
### ⚠ BREAKING CHANGES
|
||||
|
||||
* drop node 10 from engines list, update typescript to 4.6.3 (#300)
|
||||
|
||||
### Build System
|
||||
|
||||
* drop node 10 from engines list, update typescript to 4.6.3 ([#300](https://github.com/googleapis/nodejs-promisify/issues/300)) ([fed2f14](https://github.com/googleapis/nodejs-promisify/commit/fed2f145a5256c939eb66b85a5c7c48332b8841d))
|
||||
|
||||
### [2.0.4](https://www.github.com/googleapis/nodejs-promisify/compare/v2.0.3...v2.0.4) (2021-09-09)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **build:** switch primary branch to main ([#270](https://www.github.com/googleapis/nodejs-promisify/issues/270)) ([11242f7](https://www.github.com/googleapis/nodejs-promisify/commit/11242f7f76e170dae7a429f8d4064bf33be9bb3f))
|
||||
|
||||
### [2.0.3](https://www.github.com/googleapis/nodejs-promisify/compare/v2.0.2...v2.0.3) (2020-09-04)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* allow excluding accessor methods ([#228](https://www.github.com/googleapis/nodejs-promisify/issues/228)) ([114d8bc](https://www.github.com/googleapis/nodejs-promisify/commit/114d8bcef7093bdfda195a15e0c2f376195fd3fc))
|
||||
|
||||
### [2.0.2](https://www.github.com/googleapis/nodejs-promisify/compare/v2.0.1...v2.0.2) (2020-07-06)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* update node issue template ([#204](https://www.github.com/googleapis/nodejs-promisify/issues/204)) ([a2ba8d8](https://www.github.com/googleapis/nodejs-promisify/commit/a2ba8d8e45ef03d093d987292a467696745fc9fd))
|
||||
|
||||
### [2.0.1](https://www.github.com/googleapis/nodejs-promisify/compare/v2.0.0...v2.0.1) (2020-05-08)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* apache license URL ([#468](https://www.github.com/googleapis/nodejs-promisify/issues/468)) ([#191](https://www.github.com/googleapis/nodejs-promisify/issues/191)) ([0edc724](https://www.github.com/googleapis/nodejs-promisify/commit/0edc7246c53d25d9dd220b813561bcee97250783))
|
||||
|
||||
## [2.0.0](https://www.github.com/googleapis/nodejs-promisify/compare/v1.0.4...v2.0.0) (2020-03-23)
|
||||
|
||||
|
||||
### ⚠ BREAKING CHANGES
|
||||
|
||||
* update to latest version of gts/typescript (#183)
|
||||
* drop Node 8 from engines field (#184)
|
||||
|
||||
### Features
|
||||
|
||||
* drop Node 8 from engines field ([#184](https://www.github.com/googleapis/nodejs-promisify/issues/184)) ([7e6d3c5](https://www.github.com/googleapis/nodejs-promisify/commit/7e6d3c54066d89530ed25c7f9722efd252f43fb8))
|
||||
|
||||
|
||||
### Build System
|
||||
|
||||
* update to latest version of gts/typescript ([#183](https://www.github.com/googleapis/nodejs-promisify/issues/183)) ([9c3ed12](https://www.github.com/googleapis/nodejs-promisify/commit/9c3ed12c12f4bb1e17af7440c6371c4cefddcd59))
|
||||
|
||||
### [1.0.4](https://www.github.com/googleapis/nodejs-promisify/compare/v1.0.3...v1.0.4) (2019-12-05)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **deps:** pin TypeScript below 3.7.0 ([e48750e](https://www.github.com/googleapis/nodejs-promisify/commit/e48750ef96aa20eb3a2b73fe2f062d04430468a7))
|
||||
|
||||
### [1.0.3](https://www.github.com/googleapis/nodejs-promisify/compare/v1.0.2...v1.0.3) (2019-11-13)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **docs:** add jsdoc-region-tag plugin ([#146](https://www.github.com/googleapis/nodejs-promisify/issues/146)) ([ff0ee74](https://www.github.com/googleapis/nodejs-promisify/commit/ff0ee7408f50e8f7147b8ccf7e10337aa5920076))
|
||||
|
||||
### [1.0.2](https://www.github.com/googleapis/nodejs-promisify/compare/v1.0.1...v1.0.2) (2019-06-26)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **docs:** link to reference docs section on googleapis.dev ([#128](https://www.github.com/googleapis/nodejs-promisify/issues/128)) ([5a8bd90](https://www.github.com/googleapis/nodejs-promisify/commit/5a8bd90))
|
||||
|
||||
### [1.0.1](https://www.github.com/googleapis/nodejs-promisify/compare/v1.0.0...v1.0.1) (2019-06-14)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **docs:** move to new client docs URL ([#124](https://www.github.com/googleapis/nodejs-promisify/issues/124)) ([34d18cd](https://www.github.com/googleapis/nodejs-promisify/commit/34d18cd))
|
||||
|
||||
## [1.0.0](https://www.github.com/googleapis/nodejs-promisify/compare/v0.4.0...v1.0.0) (2019-05-02)
|
||||
|
||||
|
||||
### Build System
|
||||
|
||||
* upgrade engines field to >=8.10.0 ([#108](https://www.github.com/googleapis/nodejs-promisify/issues/108)) ([78ab89c](https://www.github.com/googleapis/nodejs-promisify/commit/78ab89c))
|
||||
|
||||
|
||||
### BREAKING CHANGES
|
||||
|
||||
* upgrade engines field to >=8.10.0 (#108)
|
||||
|
||||
## v0.4.0
|
||||
|
||||
02-12-2019 19:44 PST
|
||||
|
||||
### New features
|
||||
- feat: add callbackify() and callbackifyAll() methods ([#82](https://github.com/googleapis/nodejs-promisify/pull/82))
|
||||
|
||||
### Documentation
|
||||
- docs: update contributing path in README ([#86](https://github.com/googleapis/nodejs-promisify/pull/86))
|
||||
- chore: move CONTRIBUTING.md to root ([#85](https://github.com/googleapis/nodejs-promisify/pull/85))
|
||||
- docs: add lint/fix example to contributing guide ([#83](https://github.com/googleapis/nodejs-promisify/pull/83))
|
||||
|
||||
### Internal / Testing Changes
|
||||
- build: create docs test npm scripts ([#88](https://github.com/googleapis/nodejs-promisify/pull/88))
|
||||
- build: test using @grpc/grpc-js in CI ([#87](https://github.com/googleapis/nodejs-promisify/pull/87))
|
||||
- build: ignore googleapis.com in doc link check ([#81](https://github.com/googleapis/nodejs-promisify/pull/81))
|
||||
- build: check broken links in generated docs ([#79](https://github.com/googleapis/nodejs-promisify/pull/79))
|
||||
- chore(deps): update dependency @types/sinon to v7 ([#78](https://github.com/googleapis/nodejs-promisify/pull/78))
|
||||
- chore(build): inject yoshi automation key ([#77](https://github.com/googleapis/nodejs-promisify/pull/77))
|
||||
- chore: update nyc and eslint configs ([#76](https://github.com/googleapis/nodejs-promisify/pull/76))
|
||||
- chore: fix publish.sh permission +x ([#74](https://github.com/googleapis/nodejs-promisify/pull/74))
|
||||
- fix(build): fix Kokoro release script ([#73](https://github.com/googleapis/nodejs-promisify/pull/73))
|
||||
- build: add Kokoro configs for autorelease ([#72](https://github.com/googleapis/nodejs-promisify/pull/72))
|
||||
- chore: always nyc report before calling codecov ([#69](https://github.com/googleapis/nodejs-promisify/pull/69))
|
||||
- chore: nyc ignore build/test by default ([#68](https://github.com/googleapis/nodejs-promisify/pull/68))
|
||||
- chore(build): update prettier config ([#66](https://github.com/googleapis/nodejs-promisify/pull/66))
|
||||
- fix: get the build passing ([#65](https://github.com/googleapis/nodejs-promisify/pull/65))
|
||||
- chore: update license file ([#64](https://github.com/googleapis/nodejs-promisify/pull/64))
|
||||
- fix(build): fix system key decryption ([#60](https://github.com/googleapis/nodejs-promisify/pull/60))
|
||||
- chore(deps): update dependency @types/sinon to v5.0.7 ([#58](https://github.com/googleapis/nodejs-promisify/pull/58))
|
||||
- fix: Pin @types/sinon to last compatible version ([#57](https://github.com/googleapis/nodejs-promisify/pull/57))
|
||||
- chore: add synth.metadata
|
||||
- chore(deps): update dependency gts to ^0.9.0 ([#54](https://github.com/googleapis/nodejs-promisify/pull/54))
|
||||
- chore: update eslintignore config ([#53](https://github.com/googleapis/nodejs-promisify/pull/53))
|
||||
- chore: use latest npm on Windows ([#52](https://github.com/googleapis/nodejs-promisify/pull/52))
|
||||
- chore: update CircleCI config ([#51](https://github.com/googleapis/nodejs-promisify/pull/51))
|
||||
- chore: include build in eslintignore ([#48](https://github.com/googleapis/nodejs-promisify/pull/48))
|
||||
- chore: update issue templates ([#44](https://github.com/googleapis/nodejs-promisify/pull/44))
|
||||
- chore: remove old issue template ([#42](https://github.com/googleapis/nodejs-promisify/pull/42))
|
||||
- build: run tests on node11 ([#41](https://github.com/googleapis/nodejs-promisify/pull/41))
|
||||
- chores(build): do not collect sponge.xml from windows builds ([#40](https://github.com/googleapis/nodejs-promisify/pull/40))
|
||||
- chores(build): run codecov on continuous builds ([#39](https://github.com/googleapis/nodejs-promisify/pull/39))
|
||||
- chore: update new issue template ([#38](https://github.com/googleapis/nodejs-promisify/pull/38))
|
||||
- chore(deps): update dependency sinon to v7 ([#33](https://github.com/googleapis/nodejs-promisify/pull/33))
|
||||
- build: fix codecov uploading on Kokoro ([#34](https://github.com/googleapis/nodejs-promisify/pull/34))
|
||||
- Update kokoro config ([#30](https://github.com/googleapis/nodejs-promisify/pull/30))
|
||||
- Update CI config ([#28](https://github.com/googleapis/nodejs-promisify/pull/28))
|
||||
- Don't publish sourcemaps ([#26](https://github.com/googleapis/nodejs-promisify/pull/26))
|
||||
- Update kokoro config ([#24](https://github.com/googleapis/nodejs-promisify/pull/24))
|
||||
- test: remove appveyor config ([#23](https://github.com/googleapis/nodejs-promisify/pull/23))
|
||||
- Update CI config ([#22](https://github.com/googleapis/nodejs-promisify/pull/22))
|
||||
- Enable prefer-const in the eslint config ([#21](https://github.com/googleapis/nodejs-promisify/pull/21))
|
||||
- Enable no-var in eslint ([#19](https://github.com/googleapis/nodejs-promisify/pull/19))
|
||||
- Update CI config ([#18](https://github.com/googleapis/nodejs-promisify/pull/18))
|
||||
|
||||
## v0.3.1
|
||||
|
||||
### Internal / Testing Changes
|
||||
- Add synth script and update CI (#14)
|
||||
- chore(deps): update dependency nyc to v13 (#12)
|
||||
- chore: ignore package-lock.json (#11)
|
||||
- chore(deps): lock file maintenance (#10)
|
||||
- chore: update renovate config (#9)
|
||||
- remove that whitespace (#8)
|
||||
- chore(deps): lock file maintenance (#7)
|
||||
- chore(deps): update dependency typescript to v3 (#6)
|
||||
- chore: assert.deelEqual => assert.deepStrictEqual (#5)
|
||||
- chore: move mocha options to mocha.opts (#4)
|
||||
- chore(deps): update dependency gts to ^0.8.0 (#1)
|
||||
- chore(deps): lock file maintenance (#3)
|
||||
- chore(deps): lock file maintenance (#2)
|
||||
@ -0,0 +1,202 @@
|
||||
|
||||
Apache License
|
||||
Version 2.0, January 2004
|
||||
http://www.apache.org/licenses/
|
||||
|
||||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||
|
||||
1. Definitions.
|
||||
|
||||
"License" shall mean the terms and conditions for use, reproduction,
|
||||
and distribution as defined by Sections 1 through 9 of this document.
|
||||
|
||||
"Licensor" shall mean the copyright owner or entity authorized by
|
||||
the copyright owner that is granting the License.
|
||||
|
||||
"Legal Entity" shall mean the union of the acting entity and all
|
||||
other entities that control, are controlled by, or are under common
|
||||
control with that entity. For the purposes of this definition,
|
||||
"control" means (i) the power, direct or indirect, to cause the
|
||||
direction or management of such entity, whether by contract or
|
||||
otherwise, or (ii) ownership of fifty percent (50%) or more of the
|
||||
outstanding shares, or (iii) beneficial ownership of such entity.
|
||||
|
||||
"You" (or "Your") shall mean an individual or Legal Entity
|
||||
exercising permissions granted by this License.
|
||||
|
||||
"Source" form shall mean the preferred form for making modifications,
|
||||
including but not limited to software source code, documentation
|
||||
source, and configuration files.
|
||||
|
||||
"Object" form shall mean any form resulting from mechanical
|
||||
transformation or translation of a Source form, including but
|
||||
not limited to compiled object code, generated documentation,
|
||||
and conversions to other media types.
|
||||
|
||||
"Work" shall mean the work of authorship, whether in Source or
|
||||
Object form, made available under the License, as indicated by a
|
||||
copyright notice that is included in or attached to the work
|
||||
(an example is provided in the Appendix below).
|
||||
|
||||
"Derivative Works" shall mean any work, whether in Source or Object
|
||||
form, that is based on (or derived from) the Work and for which the
|
||||
editorial revisions, annotations, elaborations, or other modifications
|
||||
represent, as a whole, an original work of authorship. For the purposes
|
||||
of this License, Derivative Works shall not include works that remain
|
||||
separable from, or merely link (or bind by name) to the interfaces of,
|
||||
the Work and Derivative Works thereof.
|
||||
|
||||
"Contribution" shall mean any work of authorship, including
|
||||
the original version of the Work and any modifications or additions
|
||||
to that Work or Derivative Works thereof, that is intentionally
|
||||
submitted to Licensor for inclusion in the Work by the copyright owner
|
||||
or by an individual or Legal Entity authorized to submit on behalf of
|
||||
the copyright owner. For the purposes of this definition, "submitted"
|
||||
means any form of electronic, verbal, or written communication sent
|
||||
to the Licensor or its representatives, including but not limited to
|
||||
communication on electronic mailing lists, source code control systems,
|
||||
and issue tracking systems that are managed by, or on behalf of, the
|
||||
Licensor for the purpose of discussing and improving the Work, but
|
||||
excluding communication that is conspicuously marked or otherwise
|
||||
designated in writing by the copyright owner as "Not a Contribution."
|
||||
|
||||
"Contributor" shall mean Licensor and any individual or Legal Entity
|
||||
on behalf of whom a Contribution has been received by Licensor and
|
||||
subsequently incorporated within the Work.
|
||||
|
||||
2. Grant of Copyright License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
copyright license to reproduce, prepare Derivative Works of,
|
||||
publicly display, publicly perform, sublicense, and distribute the
|
||||
Work and such Derivative Works in Source or Object form.
|
||||
|
||||
3. Grant of Patent License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
(except as stated in this section) patent license to make, have made,
|
||||
use, offer to sell, sell, import, and otherwise transfer the Work,
|
||||
where such license applies only to those patent claims licensable
|
||||
by such Contributor that are necessarily infringed by their
|
||||
Contribution(s) alone or by combination of their Contribution(s)
|
||||
with the Work to which such Contribution(s) was submitted. If You
|
||||
institute patent litigation against any entity (including a
|
||||
cross-claim or counterclaim in a lawsuit) alleging that the Work
|
||||
or a Contribution incorporated within the Work constitutes direct
|
||||
or contributory patent infringement, then any patent licenses
|
||||
granted to You under this License for that Work shall terminate
|
||||
as of the date such litigation is filed.
|
||||
|
||||
4. Redistribution. You may reproduce and distribute copies of the
|
||||
Work or Derivative Works thereof in any medium, with or without
|
||||
modifications, and in Source or Object form, provided that You
|
||||
meet the following conditions:
|
||||
|
||||
(a) You must give any other recipients of the Work or
|
||||
Derivative Works a copy of this License; and
|
||||
|
||||
(b) You must cause any modified files to carry prominent notices
|
||||
stating that You changed the files; and
|
||||
|
||||
(c) You must retain, in the Source form of any Derivative Works
|
||||
that You distribute, all copyright, patent, trademark, and
|
||||
attribution notices from the Source form of the Work,
|
||||
excluding those notices that do not pertain to any part of
|
||||
the Derivative Works; and
|
||||
|
||||
(d) If the Work includes a "NOTICE" text file as part of its
|
||||
distribution, then any Derivative Works that You distribute must
|
||||
include a readable copy of the attribution notices contained
|
||||
within such NOTICE file, excluding those notices that do not
|
||||
pertain to any part of the Derivative Works, in at least one
|
||||
of the following places: within a NOTICE text file distributed
|
||||
as part of the Derivative Works; within the Source form or
|
||||
documentation, if provided along with the Derivative Works; or,
|
||||
within a display generated by the Derivative Works, if and
|
||||
wherever such third-party notices normally appear. The contents
|
||||
of the NOTICE file are for informational purposes only and
|
||||
do not modify the License. You may add Your own attribution
|
||||
notices within Derivative Works that You distribute, alongside
|
||||
or as an addendum to the NOTICE text from the Work, provided
|
||||
that such additional attribution notices cannot be construed
|
||||
as modifying the License.
|
||||
|
||||
You may add Your own copyright statement to Your modifications and
|
||||
may provide additional or different license terms and conditions
|
||||
for use, reproduction, or distribution of Your modifications, or
|
||||
for any such Derivative Works as a whole, provided Your use,
|
||||
reproduction, and distribution of the Work otherwise complies with
|
||||
the conditions stated in this License.
|
||||
|
||||
5. Submission of Contributions. Unless You explicitly state otherwise,
|
||||
any Contribution intentionally submitted for inclusion in the Work
|
||||
by You to the Licensor shall be under the terms and conditions of
|
||||
this License, without any additional terms or conditions.
|
||||
Notwithstanding the above, nothing herein shall supersede or modify
|
||||
the terms of any separate license agreement you may have executed
|
||||
with Licensor regarding such Contributions.
|
||||
|
||||
6. Trademarks. This License does not grant permission to use the trade
|
||||
names, trademarks, service marks, or product names of the Licensor,
|
||||
except as required for reasonable and customary use in describing the
|
||||
origin of the Work and reproducing the content of the NOTICE file.
|
||||
|
||||
7. Disclaimer of Warranty. Unless required by applicable law or
|
||||
agreed to in writing, Licensor provides the Work (and each
|
||||
Contributor provides its Contributions) on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
implied, including, without limitation, any warranties or conditions
|
||||
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
|
||||
PARTICULAR PURPOSE. You are solely responsible for determining the
|
||||
appropriateness of using or redistributing the Work and assume any
|
||||
risks associated with Your exercise of permissions under this License.
|
||||
|
||||
8. Limitation of Liability. In no event and under no legal theory,
|
||||
whether in tort (including negligence), contract, or otherwise,
|
||||
unless required by applicable law (such as deliberate and grossly
|
||||
negligent acts) or agreed to in writing, shall any Contributor be
|
||||
liable to You for damages, including any direct, indirect, special,
|
||||
incidental, or consequential damages of any character arising as a
|
||||
result of this License or out of the use or inability to use the
|
||||
Work (including but not limited to damages for loss of goodwill,
|
||||
work stoppage, computer failure or malfunction, or any and all
|
||||
other commercial damages or losses), even if such Contributor
|
||||
has been advised of the possibility of such damages.
|
||||
|
||||
9. Accepting Warranty or Additional Liability. While redistributing
|
||||
the Work or Derivative Works thereof, You may choose to offer,
|
||||
and charge a fee for, acceptance of support, warranty, indemnity,
|
||||
or other liability obligations and/or rights consistent with this
|
||||
License. However, in accepting such obligations, You may act only
|
||||
on Your own behalf and on Your sole responsibility, not on behalf
|
||||
of any other Contributor, and only if You agree to indemnify,
|
||||
defend, and hold each Contributor harmless for any liability
|
||||
incurred by, or claims asserted against, such Contributor by reason
|
||||
of your accepting any such warranty or additional liability.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
|
||||
APPENDIX: How to apply the Apache License to your work.
|
||||
|
||||
To apply the Apache License to your work, attach the following
|
||||
boilerplate notice, with the fields enclosed by brackets "[]"
|
||||
replaced with your own identifying information. (Don't include
|
||||
the brackets!) The text should be enclosed in the appropriate
|
||||
comment syntax for the file format. We also recommend that a
|
||||
file or class name and description of purpose be included on the
|
||||
same "printed page" as the copyright notice for easier
|
||||
identification within third-party archives.
|
||||
|
||||
Copyright [yyyy] [name of copyright owner]
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
@ -0,0 +1,156 @@
|
||||
[//]: # "This README.md file is auto-generated, all changes to this file will be lost."
|
||||
[//]: # "To regenerate it, use `python -m synthtool`."
|
||||
<img src="https://avatars2.githubusercontent.com/u/2810941?v=3&s=96" alt="Google Cloud Platform logo" title="Google Cloud Platform" align="right" height="96" width="96"/>
|
||||
|
||||
# [Google Cloud Common Promisify: Node.js Client](https://github.com/googleapis/nodejs-promisify)
|
||||
|
||||
[](https://cloud.google.com/terms/launch-stages)
|
||||
[](https://www.npmjs.org/package/@google-cloud/promisify)
|
||||
|
||||
|
||||
|
||||
|
||||
A simple utility for promisifying functions and classes.
|
||||
|
||||
|
||||
A comprehensive list of changes in each version may be found in
|
||||
[the CHANGELOG](https://github.com/googleapis/nodejs-promisify/blob/main/CHANGELOG.md).
|
||||
|
||||
* [Google Cloud Common Promisify Node.js Client API Reference][client-docs]
|
||||
|
||||
* [github.com/googleapis/nodejs-promisify](https://github.com/googleapis/nodejs-promisify)
|
||||
|
||||
Read more about the client libraries for Cloud APIs, including the older
|
||||
Google APIs Client Libraries, in [Client Libraries Explained][explained].
|
||||
|
||||
[explained]: https://cloud.google.com/apis/docs/client-libraries-explained
|
||||
|
||||
**Table of contents:**
|
||||
|
||||
|
||||
* [Quickstart](#quickstart)
|
||||
|
||||
* [Installing the client library](#installing-the-client-library)
|
||||
* [Using the client library](#using-the-client-library)
|
||||
* [Samples](#samples)
|
||||
* [Versioning](#versioning)
|
||||
* [Contributing](#contributing)
|
||||
* [License](#license)
|
||||
|
||||
## Quickstart
|
||||
|
||||
### Installing the client library
|
||||
|
||||
```bash
|
||||
npm install @google-cloud/promisify
|
||||
```
|
||||
|
||||
|
||||
### Using the client library
|
||||
|
||||
```javascript
|
||||
const {promisify} = require('@google-cloud/promisify');
|
||||
|
||||
/**
|
||||
* This is a very basic example function that accepts a callback.
|
||||
*/
|
||||
function someCallbackFunction(name, callback) {
|
||||
if (!name) {
|
||||
callback(new Error('Name is required!'));
|
||||
} else {
|
||||
callback(null, `Well hello there, ${name}!`);
|
||||
}
|
||||
}
|
||||
|
||||
// let's promisify it!
|
||||
const somePromiseFunction = promisify(someCallbackFunction);
|
||||
|
||||
async function quickstart() {
|
||||
// now we can just `await` the function to use it like a promisified method
|
||||
const [result] = await somePromiseFunction('nodestronaut');
|
||||
console.log(result);
|
||||
}
|
||||
quickstart();
|
||||
|
||||
```
|
||||
It's unlikely you will need to install this package directly, as it will be
|
||||
installed as a dependency when you install other `@google-cloud` packages.
|
||||
|
||||
|
||||
## Samples
|
||||
|
||||
Samples are in the [`samples/`](https://github.com/googleapis/nodejs-promisify/tree/main/samples) directory. Each sample's `README.md` has instructions for running its sample.
|
||||
|
||||
| Sample | Source Code | Try it |
|
||||
| --------------------------- | --------------------------------- | ------ |
|
||||
| Quickstart | [source code](https://github.com/googleapis/nodejs-promisify/blob/main/samples/quickstart.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-promisify&page=editor&open_in_editor=samples/quickstart.js,samples/README.md) |
|
||||
|
||||
|
||||
|
||||
The [Google Cloud Common Promisify Node.js Client API Reference][client-docs] documentation
|
||||
also contains samples.
|
||||
|
||||
## Supported Node.js Versions
|
||||
|
||||
Our client libraries follow the [Node.js release schedule](https://nodejs.org/en/about/releases/).
|
||||
Libraries are compatible with all current _active_ and _maintenance_ versions of
|
||||
Node.js.
|
||||
If you are using an end-of-life version of Node.js, we recommend that you update
|
||||
as soon as possible to an actively supported LTS version.
|
||||
|
||||
Google's client libraries support legacy versions of Node.js runtimes on a
|
||||
best-efforts basis with the following warnings:
|
||||
|
||||
* Legacy versions are not tested in continuous integration.
|
||||
* Some security patches and features cannot be backported.
|
||||
* Dependencies cannot be kept up-to-date.
|
||||
|
||||
Client libraries targeting some end-of-life versions of Node.js are available, and
|
||||
can be installed through npm [dist-tags](https://docs.npmjs.com/cli/dist-tag).
|
||||
The dist-tags follow the naming convention `legacy-(version)`.
|
||||
For example, `npm install @google-cloud/promisify@legacy-8` installs client libraries
|
||||
for versions compatible with Node.js 8.
|
||||
|
||||
## Versioning
|
||||
|
||||
This library follows [Semantic Versioning](http://semver.org/).
|
||||
|
||||
|
||||
|
||||
This library is considered to be **stable**. The code surface will not change in backwards-incompatible ways
|
||||
unless absolutely necessary (e.g. because of critical security issues) or with
|
||||
an extensive deprecation period. Issues and requests against **stable** libraries
|
||||
are addressed with the highest priority.
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
More Information: [Google Cloud Platform Launch Stages][launch_stages]
|
||||
|
||||
[launch_stages]: https://cloud.google.com/terms/launch-stages
|
||||
|
||||
## Contributing
|
||||
|
||||
Contributions welcome! See the [Contributing Guide](https://github.com/googleapis/nodejs-promisify/blob/main/CONTRIBUTING.md).
|
||||
|
||||
Please note that this `README.md`, the `samples/README.md`,
|
||||
and a variety of configuration files in this repository (including `.nycrc` and `tsconfig.json`)
|
||||
are generated from a central template. To edit one of these files, make an edit
|
||||
to its templates in
|
||||
[directory](https://github.com/googleapis/synthtool).
|
||||
|
||||
## License
|
||||
|
||||
Apache Version 2.0
|
||||
|
||||
See [LICENSE](https://github.com/googleapis/nodejs-promisify/blob/main/LICENSE)
|
||||
|
||||
[client-docs]: https://googleapis.dev/nodejs/promisify/latest
|
||||
|
||||
[shell_img]: https://gstatic.com/cloudssh/images/open-btn.png
|
||||
[projects]: https://console.cloud.google.com/project
|
||||
[billing]: https://support.google.com/cloud/answer/6293499#enable-billing
|
||||
|
||||
[auth]: https://cloud.google.com/docs/authentication/getting-started
|
||||
@ -0,0 +1,61 @@
|
||||
export interface PromisifyAllOptions extends PromisifyOptions {
|
||||
/**
|
||||
* Array of methods to ignore when promisifying.
|
||||
*/
|
||||
exclude?: string[];
|
||||
}
|
||||
export interface PromisifyOptions {
|
||||
/**
|
||||
* Resolve the promise with single arg instead of an array.
|
||||
*/
|
||||
singular?: boolean;
|
||||
}
|
||||
export interface PromiseMethod extends Function {
|
||||
promisified_?: boolean;
|
||||
}
|
||||
export interface WithPromise {
|
||||
Promise?: PromiseConstructor;
|
||||
}
|
||||
export interface CallbackifyAllOptions {
|
||||
/**
|
||||
* Array of methods to ignore when callbackifying.
|
||||
*/
|
||||
exclude?: string[];
|
||||
}
|
||||
export interface CallbackMethod extends Function {
|
||||
callbackified_?: boolean;
|
||||
}
|
||||
/**
|
||||
* Wraps a callback style function to conditionally return a promise.
|
||||
*
|
||||
* @param {function} originalMethod - The method to promisify.
|
||||
* @param {object=} options - Promise options.
|
||||
* @param {boolean} options.singular - Resolve the promise with single arg instead of an array.
|
||||
* @return {function} wrapped
|
||||
*/
|
||||
export declare function promisify(originalMethod: PromiseMethod, options?: PromisifyOptions): any;
|
||||
/**
|
||||
* Promisifies certain Class methods. This will not promisify private or
|
||||
* streaming methods.
|
||||
*
|
||||
* @param {module:common/service} Class - Service class.
|
||||
* @param {object=} options - Configuration object.
|
||||
*/
|
||||
export declare function promisifyAll(Class: Function, options?: PromisifyAllOptions): void;
|
||||
/**
|
||||
* Wraps a promisy type function to conditionally call a callback function.
|
||||
*
|
||||
* @param {function} originalMethod - The method to callbackify.
|
||||
* @param {object=} options - Callback options.
|
||||
* @param {boolean} options.singular - Pass to the callback a single arg instead of an array.
|
||||
* @return {function} wrapped
|
||||
*/
|
||||
export declare function callbackify(originalMethod: CallbackMethod): CallbackMethod;
|
||||
/**
|
||||
* Callbackifies certain Class methods. This will not callbackify private or
|
||||
* streaming methods.
|
||||
*
|
||||
* @param {module:common/service} Class - Service class.
|
||||
* @param {object=} options - Configuration object.
|
||||
*/
|
||||
export declare function callbackifyAll(Class: Function, options?: CallbackifyAllOptions): void;
|
||||
@ -0,0 +1,148 @@
|
||||
"use strict";
|
||||
/* eslint-disable prefer-rest-params */
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.callbackifyAll = exports.callbackify = exports.promisifyAll = exports.promisify = void 0;
|
||||
/**
|
||||
* Wraps a callback style function to conditionally return a promise.
|
||||
*
|
||||
* @param {function} originalMethod - The method to promisify.
|
||||
* @param {object=} options - Promise options.
|
||||
* @param {boolean} options.singular - Resolve the promise with single arg instead of an array.
|
||||
* @return {function} wrapped
|
||||
*/
|
||||
function promisify(originalMethod, options) {
|
||||
if (originalMethod.promisified_) {
|
||||
return originalMethod;
|
||||
}
|
||||
options = options || {};
|
||||
const slice = Array.prototype.slice;
|
||||
// tslint:disable-next-line:no-any
|
||||
const wrapper = function () {
|
||||
let last;
|
||||
for (last = arguments.length - 1; last >= 0; last--) {
|
||||
const arg = arguments[last];
|
||||
if (typeof arg === 'undefined') {
|
||||
continue; // skip trailing undefined.
|
||||
}
|
||||
if (typeof arg !== 'function') {
|
||||
break; // non-callback last argument found.
|
||||
}
|
||||
return originalMethod.apply(this, arguments);
|
||||
}
|
||||
// peel trailing undefined.
|
||||
const args = slice.call(arguments, 0, last + 1);
|
||||
// tslint:disable-next-line:variable-name
|
||||
let PromiseCtor = Promise;
|
||||
// Because dedupe will likely create a single install of
|
||||
// @google-cloud/common to be shared amongst all modules, we need to
|
||||
// localize it at the Service level.
|
||||
if (this && this.Promise) {
|
||||
PromiseCtor = this.Promise;
|
||||
}
|
||||
return new PromiseCtor((resolve, reject) => {
|
||||
// tslint:disable-next-line:no-any
|
||||
args.push((...args) => {
|
||||
const callbackArgs = slice.call(args);
|
||||
const err = callbackArgs.shift();
|
||||
if (err) {
|
||||
return reject(err);
|
||||
}
|
||||
if (options.singular && callbackArgs.length === 1) {
|
||||
resolve(callbackArgs[0]);
|
||||
}
|
||||
else {
|
||||
resolve(callbackArgs);
|
||||
}
|
||||
});
|
||||
originalMethod.apply(this, args);
|
||||
});
|
||||
};
|
||||
wrapper.promisified_ = true;
|
||||
return wrapper;
|
||||
}
|
||||
exports.promisify = promisify;
|
||||
/**
|
||||
* Promisifies certain Class methods. This will not promisify private or
|
||||
* streaming methods.
|
||||
*
|
||||
* @param {module:common/service} Class - Service class.
|
||||
* @param {object=} options - Configuration object.
|
||||
*/
|
||||
// tslint:disable-next-line:variable-name
|
||||
function promisifyAll(Class, options) {
|
||||
const exclude = (options && options.exclude) || [];
|
||||
const ownPropertyNames = Object.getOwnPropertyNames(Class.prototype);
|
||||
const methods = ownPropertyNames.filter(methodName => {
|
||||
// clang-format off
|
||||
return (!exclude.includes(methodName) &&
|
||||
typeof Class.prototype[methodName] === 'function' && // is it a function?
|
||||
!/(^_|(Stream|_)|promise$)|^constructor$/.test(methodName) // is it promisable?
|
||||
);
|
||||
// clang-format on
|
||||
});
|
||||
methods.forEach(methodName => {
|
||||
const originalMethod = Class.prototype[methodName];
|
||||
if (!originalMethod.promisified_) {
|
||||
Class.prototype[methodName] = exports.promisify(originalMethod, options);
|
||||
}
|
||||
});
|
||||
}
|
||||
exports.promisifyAll = promisifyAll;
|
||||
/**
|
||||
* Wraps a promisy type function to conditionally call a callback function.
|
||||
*
|
||||
* @param {function} originalMethod - The method to callbackify.
|
||||
* @param {object=} options - Callback options.
|
||||
* @param {boolean} options.singular - Pass to the callback a single arg instead of an array.
|
||||
* @return {function} wrapped
|
||||
*/
|
||||
function callbackify(originalMethod) {
|
||||
if (originalMethod.callbackified_) {
|
||||
return originalMethod;
|
||||
}
|
||||
// tslint:disable-next-line:no-any
|
||||
const wrapper = function () {
|
||||
if (typeof arguments[arguments.length - 1] !== 'function') {
|
||||
return originalMethod.apply(this, arguments);
|
||||
}
|
||||
const cb = Array.prototype.pop.call(arguments);
|
||||
originalMethod.apply(this, arguments).then(
|
||||
// tslint:disable-next-line:no-any
|
||||
(res) => {
|
||||
res = Array.isArray(res) ? res : [res];
|
||||
cb(null, ...res);
|
||||
}, (err) => cb(err));
|
||||
};
|
||||
wrapper.callbackified_ = true;
|
||||
return wrapper;
|
||||
}
|
||||
exports.callbackify = callbackify;
|
||||
/**
|
||||
* Callbackifies certain Class methods. This will not callbackify private or
|
||||
* streaming methods.
|
||||
*
|
||||
* @param {module:common/service} Class - Service class.
|
||||
* @param {object=} options - Configuration object.
|
||||
*/
|
||||
function callbackifyAll(
|
||||
// tslint:disable-next-line:variable-name
|
||||
Class, options) {
|
||||
const exclude = (options && options.exclude) || [];
|
||||
const ownPropertyNames = Object.getOwnPropertyNames(Class.prototype);
|
||||
const methods = ownPropertyNames.filter(methodName => {
|
||||
// clang-format off
|
||||
return (!exclude.includes(methodName) &&
|
||||
typeof Class.prototype[methodName] === 'function' && // is it a function?
|
||||
!/^_|(Stream|_)|^constructor$/.test(methodName) // is it callbackifyable?
|
||||
);
|
||||
// clang-format on
|
||||
});
|
||||
methods.forEach(methodName => {
|
||||
const originalMethod = Class.prototype[methodName];
|
||||
if (!originalMethod.callbackified_) {
|
||||
Class.prototype[methodName] = exports.callbackify(originalMethod);
|
||||
}
|
||||
});
|
||||
}
|
||||
exports.callbackifyAll = callbackifyAll;
|
||||
//# sourceMappingURL=index.js.map
|
||||
@ -0,0 +1,50 @@
|
||||
{
|
||||
"name": "@google-cloud/promisify",
|
||||
"version": "3.0.1",
|
||||
"description": "A simple utility for promisifying functions and classes.",
|
||||
"main": "build/src/index.js",
|
||||
"types": "build/src/index.d.ts",
|
||||
"repository": "googleapis/nodejs-promisify",
|
||||
"scripts": {
|
||||
"test": "c8 mocha build/test",
|
||||
"lint": "gts check",
|
||||
"compile": "tsc -p .",
|
||||
"fix": "gts fix",
|
||||
"prepare": "npm run compile",
|
||||
"pretest": "npm run compile",
|
||||
"docs": "compodoc src/",
|
||||
"presystem-test": "npm run compile",
|
||||
"samples-test": "cd samples/ && npm link ../ && npm test && cd ../",
|
||||
"system-test": "mocha build/system-test",
|
||||
"docs-test": "linkinator docs",
|
||||
"predocs-test": "npm run docs",
|
||||
"prelint": "cd samples; npm link ../; npm install",
|
||||
"clean": "gts clean",
|
||||
"precompile": "gts clean"
|
||||
},
|
||||
"keywords": [],
|
||||
"files": [
|
||||
"build/src",
|
||||
"!build/src/**/*.map"
|
||||
],
|
||||
"author": "Google Inc.",
|
||||
"license": "Apache-2.0",
|
||||
"devDependencies": {
|
||||
"@compodoc/compodoc": "^1.1.9",
|
||||
"@types/mocha": "^9.0.0",
|
||||
"@types/node": "^17.0.25",
|
||||
"@types/sinon": "^10.0.0",
|
||||
"c8": "^7.0.0",
|
||||
"chai": "^4.2.0",
|
||||
"codecov": "^3.0.4",
|
||||
"gts": "^3.1.0",
|
||||
"hard-rejection": "^2.1.0",
|
||||
"linkinator": "^4.0.0",
|
||||
"mocha": "^8.0.0",
|
||||
"sinon": "^14.0.0",
|
||||
"typescript": "^4.6.3"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,202 @@
|
||||
|
||||
Apache License
|
||||
Version 2.0, January 2004
|
||||
http://www.apache.org/licenses/
|
||||
|
||||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||
|
||||
1. Definitions.
|
||||
|
||||
"License" shall mean the terms and conditions for use, reproduction,
|
||||
and distribution as defined by Sections 1 through 9 of this document.
|
||||
|
||||
"Licensor" shall mean the copyright owner or entity authorized by
|
||||
the copyright owner that is granting the License.
|
||||
|
||||
"Legal Entity" shall mean the union of the acting entity and all
|
||||
other entities that control, are controlled by, or are under common
|
||||
control with that entity. For the purposes of this definition,
|
||||
"control" means (i) the power, direct or indirect, to cause the
|
||||
direction or management of such entity, whether by contract or
|
||||
otherwise, or (ii) ownership of fifty percent (50%) or more of the
|
||||
outstanding shares, or (iii) beneficial ownership of such entity.
|
||||
|
||||
"You" (or "Your") shall mean an individual or Legal Entity
|
||||
exercising permissions granted by this License.
|
||||
|
||||
"Source" form shall mean the preferred form for making modifications,
|
||||
including but not limited to software source code, documentation
|
||||
source, and configuration files.
|
||||
|
||||
"Object" form shall mean any form resulting from mechanical
|
||||
transformation or translation of a Source form, including but
|
||||
not limited to compiled object code, generated documentation,
|
||||
and conversions to other media types.
|
||||
|
||||
"Work" shall mean the work of authorship, whether in Source or
|
||||
Object form, made available under the License, as indicated by a
|
||||
copyright notice that is included in or attached to the work
|
||||
(an example is provided in the Appendix below).
|
||||
|
||||
"Derivative Works" shall mean any work, whether in Source or Object
|
||||
form, that is based on (or derived from) the Work and for which the
|
||||
editorial revisions, annotations, elaborations, or other modifications
|
||||
represent, as a whole, an original work of authorship. For the purposes
|
||||
of this License, Derivative Works shall not include works that remain
|
||||
separable from, or merely link (or bind by name) to the interfaces of,
|
||||
the Work and Derivative Works thereof.
|
||||
|
||||
"Contribution" shall mean any work of authorship, including
|
||||
the original version of the Work and any modifications or additions
|
||||
to that Work or Derivative Works thereof, that is intentionally
|
||||
submitted to Licensor for inclusion in the Work by the copyright owner
|
||||
or by an individual or Legal Entity authorized to submit on behalf of
|
||||
the copyright owner. For the purposes of this definition, "submitted"
|
||||
means any form of electronic, verbal, or written communication sent
|
||||
to the Licensor or its representatives, including but not limited to
|
||||
communication on electronic mailing lists, source code control systems,
|
||||
and issue tracking systems that are managed by, or on behalf of, the
|
||||
Licensor for the purpose of discussing and improving the Work, but
|
||||
excluding communication that is conspicuously marked or otherwise
|
||||
designated in writing by the copyright owner as "Not a Contribution."
|
||||
|
||||
"Contributor" shall mean Licensor and any individual or Legal Entity
|
||||
on behalf of whom a Contribution has been received by Licensor and
|
||||
subsequently incorporated within the Work.
|
||||
|
||||
2. Grant of Copyright License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
copyright license to reproduce, prepare Derivative Works of,
|
||||
publicly display, publicly perform, sublicense, and distribute the
|
||||
Work and such Derivative Works in Source or Object form.
|
||||
|
||||
3. Grant of Patent License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
(except as stated in this section) patent license to make, have made,
|
||||
use, offer to sell, sell, import, and otherwise transfer the Work,
|
||||
where such license applies only to those patent claims licensable
|
||||
by such Contributor that are necessarily infringed by their
|
||||
Contribution(s) alone or by combination of their Contribution(s)
|
||||
with the Work to which such Contribution(s) was submitted. If You
|
||||
institute patent litigation against any entity (including a
|
||||
cross-claim or counterclaim in a lawsuit) alleging that the Work
|
||||
or a Contribution incorporated within the Work constitutes direct
|
||||
or contributory patent infringement, then any patent licenses
|
||||
granted to You under this License for that Work shall terminate
|
||||
as of the date such litigation is filed.
|
||||
|
||||
4. Redistribution. You may reproduce and distribute copies of the
|
||||
Work or Derivative Works thereof in any medium, with or without
|
||||
modifications, and in Source or Object form, provided that You
|
||||
meet the following conditions:
|
||||
|
||||
(a) You must give any other recipients of the Work or
|
||||
Derivative Works a copy of this License; and
|
||||
|
||||
(b) You must cause any modified files to carry prominent notices
|
||||
stating that You changed the files; and
|
||||
|
||||
(c) You must retain, in the Source form of any Derivative Works
|
||||
that You distribute, all copyright, patent, trademark, and
|
||||
attribution notices from the Source form of the Work,
|
||||
excluding those notices that do not pertain to any part of
|
||||
the Derivative Works; and
|
||||
|
||||
(d) If the Work includes a "NOTICE" text file as part of its
|
||||
distribution, then any Derivative Works that You distribute must
|
||||
include a readable copy of the attribution notices contained
|
||||
within such NOTICE file, excluding those notices that do not
|
||||
pertain to any part of the Derivative Works, in at least one
|
||||
of the following places: within a NOTICE text file distributed
|
||||
as part of the Derivative Works; within the Source form or
|
||||
documentation, if provided along with the Derivative Works; or,
|
||||
within a display generated by the Derivative Works, if and
|
||||
wherever such third-party notices normally appear. The contents
|
||||
of the NOTICE file are for informational purposes only and
|
||||
do not modify the License. You may add Your own attribution
|
||||
notices within Derivative Works that You distribute, alongside
|
||||
or as an addendum to the NOTICE text from the Work, provided
|
||||
that such additional attribution notices cannot be construed
|
||||
as modifying the License.
|
||||
|
||||
You may add Your own copyright statement to Your modifications and
|
||||
may provide additional or different license terms and conditions
|
||||
for use, reproduction, or distribution of Your modifications, or
|
||||
for any such Derivative Works as a whole, provided Your use,
|
||||
reproduction, and distribution of the Work otherwise complies with
|
||||
the conditions stated in this License.
|
||||
|
||||
5. Submission of Contributions. Unless You explicitly state otherwise,
|
||||
any Contribution intentionally submitted for inclusion in the Work
|
||||
by You to the Licensor shall be under the terms and conditions of
|
||||
this License, without any additional terms or conditions.
|
||||
Notwithstanding the above, nothing herein shall supersede or modify
|
||||
the terms of any separate license agreement you may have executed
|
||||
with Licensor regarding such Contributions.
|
||||
|
||||
6. Trademarks. This License does not grant permission to use the trade
|
||||
names, trademarks, service marks, or product names of the Licensor,
|
||||
except as required for reasonable and customary use in describing the
|
||||
origin of the Work and reproducing the content of the NOTICE file.
|
||||
|
||||
7. Disclaimer of Warranty. Unless required by applicable law or
|
||||
agreed to in writing, Licensor provides the Work (and each
|
||||
Contributor provides its Contributions) on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
implied, including, without limitation, any warranties or conditions
|
||||
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
|
||||
PARTICULAR PURPOSE. You are solely responsible for determining the
|
||||
appropriateness of using or redistributing the Work and assume any
|
||||
risks associated with Your exercise of permissions under this License.
|
||||
|
||||
8. Limitation of Liability. In no event and under no legal theory,
|
||||
whether in tort (including negligence), contract, or otherwise,
|
||||
unless required by applicable law (such as deliberate and grossly
|
||||
negligent acts) or agreed to in writing, shall any Contributor be
|
||||
liable to You for damages, including any direct, indirect, special,
|
||||
incidental, or consequential damages of any character arising as a
|
||||
result of this License or out of the use or inability to use the
|
||||
Work (including but not limited to damages for loss of goodwill,
|
||||
work stoppage, computer failure or malfunction, or any and all
|
||||
other commercial damages or losses), even if such Contributor
|
||||
has been advised of the possibility of such damages.
|
||||
|
||||
9. Accepting Warranty or Additional Liability. While redistributing
|
||||
the Work or Derivative Works thereof, You may choose to offer,
|
||||
and charge a fee for, acceptance of support, warranty, indemnity,
|
||||
or other liability obligations and/or rights consistent with this
|
||||
License. However, in accepting such obligations, You may act only
|
||||
on Your own behalf and on Your sole responsibility, not on behalf
|
||||
of any other Contributor, and only if You agree to indemnify,
|
||||
defend, and hold each Contributor harmless for any liability
|
||||
incurred by, or claims asserted against, such Contributor by reason
|
||||
of your accepting any such warranty or additional liability.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
|
||||
APPENDIX: How to apply the Apache License to your work.
|
||||
|
||||
To apply the Apache License to your work, attach the following
|
||||
boilerplate notice, with the fields enclosed by brackets "[]"
|
||||
replaced with your own identifying information. (Don't include
|
||||
the brackets!) The text should be enclosed in the appropriate
|
||||
comment syntax for the file format. We also recommend that a
|
||||
file or class name and description of purpose be included on the
|
||||
same "printed page" as the copyright notice for easier
|
||||
identification within third-party archives.
|
||||
|
||||
Copyright [yyyy] [name of copyright owner]
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
@ -0,0 +1,287 @@
|
||||
[//]: # "This README.md file is auto-generated, all changes to this file will be lost."
|
||||
[//]: # "To regenerate it, use `python -m synthtool`."
|
||||
<img src="https://avatars2.githubusercontent.com/u/2810941?v=3&s=96" alt="Google Cloud Platform logo" title="Google Cloud Platform" align="right" height="96" width="96"/>
|
||||
|
||||
# [Google Cloud Storage: Node.js Client](https://github.com/googleapis/nodejs-storage)
|
||||
|
||||
[](https://cloud.google.com/terms/launch-stages)
|
||||
[](https://www.npmjs.org/package/@google-cloud/storage)
|
||||
|
||||
|
||||
|
||||
|
||||
> Node.js idiomatic client for [Cloud Storage][product-docs].
|
||||
|
||||
[Cloud Storage](https://cloud.google.com/storage/docs) allows world-wide
|
||||
storage and retrieval of any amount of data at any time. You can use Google
|
||||
Cloud Storage for a range of scenarios including serving website content,
|
||||
storing data for archival and disaster recovery, or distributing large data
|
||||
objects to users via direct download.
|
||||
|
||||
|
||||
A comprehensive list of changes in each version may be found in
|
||||
[the CHANGELOG](https://github.com/googleapis/nodejs-storage/blob/main/CHANGELOG.md).
|
||||
|
||||
* [Google Cloud Storage Node.js Client API Reference][client-docs]
|
||||
* [Google Cloud Storage Documentation][product-docs]
|
||||
* [github.com/googleapis/nodejs-storage](https://github.com/googleapis/nodejs-storage)
|
||||
|
||||
Read more about the client libraries for Cloud APIs, including the older
|
||||
Google APIs Client Libraries, in [Client Libraries Explained][explained].
|
||||
|
||||
[explained]: https://cloud.google.com/apis/docs/client-libraries-explained
|
||||
|
||||
**Table of contents:**
|
||||
|
||||
|
||||
* [Quickstart](#quickstart)
|
||||
* [Before you begin](#before-you-begin)
|
||||
* [Installing the client library](#installing-the-client-library)
|
||||
* [Using the client library](#using-the-client-library)
|
||||
* [Samples](#samples)
|
||||
* [Versioning](#versioning)
|
||||
* [Contributing](#contributing)
|
||||
* [License](#license)
|
||||
|
||||
## Quickstart
|
||||
|
||||
### Before you begin
|
||||
|
||||
1. [Select or create a Cloud Platform project][projects].
|
||||
1. [Enable billing for your project][billing].
|
||||
1. [Enable the Google Cloud Storage API][enable_api].
|
||||
1. [Set up authentication with a service account][auth] so you can access the
|
||||
API from your local workstation.
|
||||
|
||||
### Installing the client library
|
||||
|
||||
```bash
|
||||
npm install @google-cloud/storage
|
||||
```
|
||||
|
||||
|
||||
### Using the client library
|
||||
|
||||
```javascript
|
||||
// Imports the Google Cloud client library
|
||||
const {Storage} = require('@google-cloud/storage');
|
||||
|
||||
// For more information on ways to initialize Storage, please see
|
||||
// https://googleapis.dev/nodejs/storage/latest/Storage.html
|
||||
|
||||
// Creates a client using Application Default Credentials
|
||||
const storage = new Storage();
|
||||
|
||||
// Creates a client from a Google service account key
|
||||
// const storage = new Storage({keyFilename: 'key.json'});
|
||||
|
||||
/**
|
||||
* TODO(developer): Uncomment these variables before running the sample.
|
||||
*/
|
||||
// The ID of your GCS bucket
|
||||
// const bucketName = 'your-unique-bucket-name';
|
||||
|
||||
async function createBucket() {
|
||||
// Creates the new bucket
|
||||
await storage.createBucket(bucketName);
|
||||
console.log(`Bucket ${bucketName} created.`);
|
||||
}
|
||||
|
||||
createBucket().catch(console.error);
|
||||
|
||||
```
|
||||
|
||||
|
||||
|
||||
## Samples
|
||||
|
||||
Samples are in the [`samples/`](https://github.com/googleapis/nodejs-storage/tree/main/samples) directory. Each sample's `README.md` has instructions for running its sample.
|
||||
|
||||
| Sample | Source Code | Try it |
|
||||
| --------------------------- | --------------------------------- | ------ |
|
||||
| Add Bucket Conditional Binding | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/addBucketConditionalBinding.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/addBucketConditionalBinding.js,samples/README.md) |
|
||||
| Add Bucket Default Owner Acl | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/addBucketDefaultOwnerAcl.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/addBucketDefaultOwnerAcl.js,samples/README.md) |
|
||||
| Add Bucket Iam Member | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/addBucketIamMember.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/addBucketIamMember.js,samples/README.md) |
|
||||
| Storage Add Bucket Label. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/addBucketLabel.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/addBucketLabel.js,samples/README.md) |
|
||||
| Add Bucket Owner Acl | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/addBucketOwnerAcl.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/addBucketOwnerAcl.js,samples/README.md) |
|
||||
| Bucket Website Configuration. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/addBucketWebsiteConfiguration.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/addBucketWebsiteConfiguration.js,samples/README.md) |
|
||||
| Add File Owner Acl | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/addFileOwnerAcl.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/addFileOwnerAcl.js,samples/README.md) |
|
||||
| Storage Get Bucket Metadata. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/bucketMetadata.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/bucketMetadata.js,samples/README.md) |
|
||||
| Change Bucket's Default Storage Class. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/changeDefaultStorageClass.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/changeDefaultStorageClass.js,samples/README.md) |
|
||||
| Storage File Convert CSEK to CMEK. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/changeFileCSEKToCMEK.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/changeFileCSEKToCMEK.js,samples/README.md) |
|
||||
| Storage Combine files. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/composeFile.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/composeFile.js,samples/README.md) |
|
||||
| Storage Configure Bucket Cors. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/configureBucketCors.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/configureBucketCors.js,samples/README.md) |
|
||||
| Configure Retries | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/configureRetries.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/configureRetries.js,samples/README.md) |
|
||||
| Copy File | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/copyFile.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/copyFile.js,samples/README.md) |
|
||||
| Copy Old Version Of File. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/copyOldVersionOfFile.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/copyOldVersionOfFile.js,samples/README.md) |
|
||||
| Create a Dual-Region Bucket | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/createBucketWithDualRegion.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/createBucketWithDualRegion.js,samples/README.md) |
|
||||
| Create Bucket With Storage Class and Location. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/createBucketWithStorageClassAndLocation.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/createBucketWithStorageClassAndLocation.js,samples/README.md) |
|
||||
| Create Bucket With Turbo Replication | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/createBucketWithTurboReplication.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/createBucketWithTurboReplication.js,samples/README.md) |
|
||||
| Create New Bucket | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/createNewBucket.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/createNewBucket.js,samples/README.md) |
|
||||
| Create Notification | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/createNotification.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/createNotification.js,samples/README.md) |
|
||||
| Delete Bucket | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/deleteBucket.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/deleteBucket.js,samples/README.md) |
|
||||
| Delete File | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/deleteFile.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/deleteFile.js,samples/README.md) |
|
||||
| Delete Notification | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/deleteNotification.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/deleteNotification.js,samples/README.md) |
|
||||
| Delete Old Version Of File. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/deleteOldVersionOfFile.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/deleteOldVersionOfFile.js,samples/README.md) |
|
||||
| Disable Bucket Lifecycle Management | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/disableBucketLifecycleManagement.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/disableBucketLifecycleManagement.js,samples/README.md) |
|
||||
| Storage Disable Bucket Versioning. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/disableBucketVersioning.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/disableBucketVersioning.js,samples/README.md) |
|
||||
| Disable Default Event Based Hold | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/disableDefaultEventBasedHold.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/disableDefaultEventBasedHold.js,samples/README.md) |
|
||||
| Disable Requester Pays | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/disableRequesterPays.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/disableRequesterPays.js,samples/README.md) |
|
||||
| Disable Uniform Bucket Level Access | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/disableUniformBucketLevelAccess.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/disableUniformBucketLevelAccess.js,samples/README.md) |
|
||||
| Download Byte Range | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/downloadByteRange.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/downloadByteRange.js,samples/README.md) |
|
||||
| Download Encrypted File | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/downloadEncryptedFile.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/downloadEncryptedFile.js,samples/README.md) |
|
||||
| Download File | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/downloadFile.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/downloadFile.js,samples/README.md) |
|
||||
| Download a File in Chunks Utilzing Transfer Manager | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/downloadFileInChunksWithTransferManager.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/downloadFileInChunksWithTransferManager.js,samples/README.md) |
|
||||
| Download File Using Requester Pays | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/downloadFileUsingRequesterPays.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/downloadFileUsingRequesterPays.js,samples/README.md) |
|
||||
| Download Folder With Transfer Manager | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/downloadFolderWithTransferManager.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/downloadFolderWithTransferManager.js,samples/README.md) |
|
||||
| Download Into Memory | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/downloadIntoMemory.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/downloadIntoMemory.js,samples/README.md) |
|
||||
| Download Many Files With Transfer Manager | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/downloadManyFilesWithTransferManager.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/downloadManyFilesWithTransferManager.js,samples/README.md) |
|
||||
| Storage Download Public File. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/downloadPublicFile.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/downloadPublicFile.js,samples/README.md) |
|
||||
| Enable Bucket Lifecycle Management | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/enableBucketLifecycleManagement.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/enableBucketLifecycleManagement.js,samples/README.md) |
|
||||
| Storage Enable Bucket Versioning. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/enableBucketVersioning.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/enableBucketVersioning.js,samples/README.md) |
|
||||
| Enable Default Event Based Hold | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/enableDefaultEventBasedHold.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/enableDefaultEventBasedHold.js,samples/README.md) |
|
||||
| Enable Default KMS Key | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/enableDefaultKMSKey.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/enableDefaultKMSKey.js,samples/README.md) |
|
||||
| Enable Requester Pays | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/enableRequesterPays.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/enableRequesterPays.js,samples/README.md) |
|
||||
| Enable Uniform Bucket Level Access | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/enableUniformBucketLevelAccess.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/enableUniformBucketLevelAccess.js,samples/README.md) |
|
||||
| Change File's Storage Class. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/fileChangeStorageClass.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/fileChangeStorageClass.js,samples/README.md) |
|
||||
| Storage Set File Metadata. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/fileSetMetadata.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/fileSetMetadata.js,samples/README.md) |
|
||||
| Generate Encryption Key | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/generateEncryptionKey.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/generateEncryptionKey.js,samples/README.md) |
|
||||
| Generate Signed Url | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/generateSignedUrl.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/generateSignedUrl.js,samples/README.md) |
|
||||
| Generate V4 Read Signed Url | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/generateV4ReadSignedUrl.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/generateV4ReadSignedUrl.js,samples/README.md) |
|
||||
| Generate V4 Signed Policy | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/generateV4SignedPolicy.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/generateV4SignedPolicy.js,samples/README.md) |
|
||||
| Generate V4 Upload Signed Url | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/generateV4UploadSignedUrl.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/generateV4UploadSignedUrl.js,samples/README.md) |
|
||||
| Get Autoclass | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/getAutoclass.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/getAutoclass.js,samples/README.md) |
|
||||
| Get Default Event Based Hold | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/getDefaultEventBasedHold.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/getDefaultEventBasedHold.js,samples/README.md) |
|
||||
| Get Metadata | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/getMetadata.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/getMetadata.js,samples/README.md) |
|
||||
| Get Metadata Notifications | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/getMetadataNotifications.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/getMetadataNotifications.js,samples/README.md) |
|
||||
| Get Public Access Prevention | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/getPublicAccessPrevention.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/getPublicAccessPrevention.js,samples/README.md) |
|
||||
| Get RPO | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/getRPO.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/getRPO.js,samples/README.md) |
|
||||
| Get Requester Pays Status | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/getRequesterPaysStatus.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/getRequesterPaysStatus.js,samples/README.md) |
|
||||
| Get Retention Policy | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/getRetentionPolicy.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/getRetentionPolicy.js,samples/README.md) |
|
||||
| Storage Get Service Account. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/getServiceAccount.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/getServiceAccount.js,samples/README.md) |
|
||||
| Get Uniform Bucket Level Access | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/getUniformBucketLevelAccess.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/getUniformBucketLevelAccess.js,samples/README.md) |
|
||||
| Activate HMAC SA Key. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/hmacKeyActivate.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/hmacKeyActivate.js,samples/README.md) |
|
||||
| Create HMAC SA Key. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/hmacKeyCreate.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/hmacKeyCreate.js,samples/README.md) |
|
||||
| Deactivate HMAC SA Key. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/hmacKeyDeactivate.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/hmacKeyDeactivate.js,samples/README.md) |
|
||||
| Delete HMAC SA Key. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/hmacKeyDelete.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/hmacKeyDelete.js,samples/README.md) |
|
||||
| Get HMAC SA Key Metadata. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/hmacKeyGet.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/hmacKeyGet.js,samples/README.md) |
|
||||
| List HMAC SA Keys Metadata. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/hmacKeysList.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/hmacKeysList.js,samples/README.md) |
|
||||
| List Buckets | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/listBuckets.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/listBuckets.js,samples/README.md) |
|
||||
| List Files | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/listFiles.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/listFiles.js,samples/README.md) |
|
||||
| List Files By Prefix | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/listFilesByPrefix.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/listFilesByPrefix.js,samples/README.md) |
|
||||
| List Files Paginate | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/listFilesPaginate.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/listFilesPaginate.js,samples/README.md) |
|
||||
| List Files with Old Versions. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/listFilesWithOldVersions.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/listFilesWithOldVersions.js,samples/README.md) |
|
||||
| List Notifications | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/listNotifications.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/listNotifications.js,samples/README.md) |
|
||||
| Lock Retention Policy | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/lockRetentionPolicy.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/lockRetentionPolicy.js,samples/README.md) |
|
||||
| Storage Make Bucket Public. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/makeBucketPublic.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/makeBucketPublic.js,samples/README.md) |
|
||||
| Make Public | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/makePublic.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/makePublic.js,samples/README.md) |
|
||||
| Move File | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/moveFile.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/moveFile.js,samples/README.md) |
|
||||
| Print Bucket Acl | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/printBucketAcl.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/printBucketAcl.js,samples/README.md) |
|
||||
| Print Bucket Acl For User | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/printBucketAclForUser.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/printBucketAclForUser.js,samples/README.md) |
|
||||
| Print File Acl | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/printFileAcl.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/printFileAcl.js,samples/README.md) |
|
||||
| Print File Acl For User | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/printFileAclForUser.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/printFileAclForUser.js,samples/README.md) |
|
||||
| Quickstart | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/quickstart.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/quickstart.js,samples/README.md) |
|
||||
| Release Event Based Hold | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/releaseEventBasedHold.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/releaseEventBasedHold.js,samples/README.md) |
|
||||
| Release Temporary Hold | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/releaseTemporaryHold.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/releaseTemporaryHold.js,samples/README.md) |
|
||||
| Remove Bucket Conditional Binding | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/removeBucketConditionalBinding.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/removeBucketConditionalBinding.js,samples/README.md) |
|
||||
| Storage Remove Bucket Cors Configuration. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/removeBucketCors.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/removeBucketCors.js,samples/README.md) |
|
||||
| Remove Bucket Default Owner | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/removeBucketDefaultOwner.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/removeBucketDefaultOwner.js,samples/README.md) |
|
||||
| Remove Bucket Iam Member | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/removeBucketIamMember.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/removeBucketIamMember.js,samples/README.md) |
|
||||
| Storage Remove Bucket Label. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/removeBucketLabel.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/removeBucketLabel.js,samples/README.md) |
|
||||
| Remove Bucket Owner Acl | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/removeBucketOwnerAcl.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/removeBucketOwnerAcl.js,samples/README.md) |
|
||||
| Remove Default KMS Key. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/removeDefaultKMSKey.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/removeDefaultKMSKey.js,samples/README.md) |
|
||||
| Remove File Owner Acl | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/removeFileOwnerAcl.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/removeFileOwnerAcl.js,samples/README.md) |
|
||||
| Remove Retention Policy | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/removeRetentionPolicy.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/removeRetentionPolicy.js,samples/README.md) |
|
||||
| Rename File | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/renameFile.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/renameFile.js,samples/README.md) |
|
||||
| Rotate Encryption Key | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/rotateEncryptionKey.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/rotateEncryptionKey.js,samples/README.md) |
|
||||
| Set Autoclass | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/setAutoclass.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/setAutoclass.js,samples/README.md) |
|
||||
| Set Client Endpoint | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/setClientEndpoint.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/setClientEndpoint.js,samples/README.md) |
|
||||
| Set Event Based Hold | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/setEventBasedHold.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/setEventBasedHold.js,samples/README.md) |
|
||||
| Set Public Access Prevention Enforced | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/setPublicAccessPreventionEnforced.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/setPublicAccessPreventionEnforced.js,samples/README.md) |
|
||||
| Set Public Access Prevention Inherited | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/setPublicAccessPreventionInherited.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/setPublicAccessPreventionInherited.js,samples/README.md) |
|
||||
| Set RPO Async Turbo | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/setRPOAsyncTurbo.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/setRPOAsyncTurbo.js,samples/README.md) |
|
||||
| Set RPO Default | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/setRPODefault.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/setRPODefault.js,samples/README.md) |
|
||||
| Set Retention Policy | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/setRetentionPolicy.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/setRetentionPolicy.js,samples/README.md) |
|
||||
| Set Temporary Hold | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/setTemporaryHold.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/setTemporaryHold.js,samples/README.md) |
|
||||
| Stream File Download | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/streamFileDownload.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/streamFileDownload.js,samples/README.md) |
|
||||
| Stream File Upload | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/streamFileUpload.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/streamFileUpload.js,samples/README.md) |
|
||||
| Upload a directory to a bucket. | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/uploadDirectory.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/uploadDirectory.js,samples/README.md) |
|
||||
| Upload Directory With Transfer Manager | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/uploadDirectoryWithTransferManager.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/uploadDirectoryWithTransferManager.js,samples/README.md) |
|
||||
| Upload Encrypted File | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/uploadEncryptedFile.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/uploadEncryptedFile.js,samples/README.md) |
|
||||
| Upload File | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/uploadFile.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/uploadFile.js,samples/README.md) |
|
||||
| Upload File With Kms Key | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/uploadFileWithKmsKey.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/uploadFileWithKmsKey.js,samples/README.md) |
|
||||
| Upload From Memory | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/uploadFromMemory.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/uploadFromMemory.js,samples/README.md) |
|
||||
| Upload Many Files With Transfer Manager | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/uploadManyFilesWithTransferManager.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/uploadManyFilesWithTransferManager.js,samples/README.md) |
|
||||
| Upload Without Authentication | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/uploadWithoutAuthentication.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/uploadWithoutAuthentication.js,samples/README.md) |
|
||||
| Upload Without Authentication Signed Url | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/uploadWithoutAuthenticationSignedUrl.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/uploadWithoutAuthenticationSignedUrl.js,samples/README.md) |
|
||||
| View Bucket Iam Members | [source code](https://github.com/googleapis/nodejs-storage/blob/main/samples/viewBucketIamMembers.js) | [![Open in Cloud Shell][shell_img]](https://console.cloud.google.com/cloudshell/open?git_repo=https://github.com/googleapis/nodejs-storage&page=editor&open_in_editor=samples/viewBucketIamMembers.js,samples/README.md) |
|
||||
|
||||
|
||||
|
||||
The [Google Cloud Storage Node.js Client API Reference][client-docs] documentation
|
||||
also contains samples.
|
||||
|
||||
## Supported Node.js Versions
|
||||
|
||||
Our client libraries follow the [Node.js release schedule](https://nodejs.org/en/about/releases/).
|
||||
Libraries are compatible with all current _active_ and _maintenance_ versions of
|
||||
Node.js.
|
||||
If you are using an end-of-life version of Node.js, we recommend that you update
|
||||
as soon as possible to an actively supported LTS version.
|
||||
|
||||
Google's client libraries support legacy versions of Node.js runtimes on a
|
||||
best-efforts basis with the following warnings:
|
||||
|
||||
* Legacy versions are not tested in continuous integration.
|
||||
* Some security patches and features cannot be backported.
|
||||
* Dependencies cannot be kept up-to-date.
|
||||
|
||||
Client libraries targeting some end-of-life versions of Node.js are available, and
|
||||
can be installed through npm [dist-tags](https://docs.npmjs.com/cli/dist-tag).
|
||||
The dist-tags follow the naming convention `legacy-(version)`.
|
||||
For example, `npm install @google-cloud/storage@legacy-8` installs client libraries
|
||||
for versions compatible with Node.js 8.
|
||||
|
||||
## Versioning
|
||||
|
||||
This library follows [Semantic Versioning](http://semver.org/).
|
||||
|
||||
|
||||
|
||||
This library is considered to be **stable**. The code surface will not change in backwards-incompatible ways
|
||||
unless absolutely necessary (e.g. because of critical security issues) or with
|
||||
an extensive deprecation period. Issues and requests against **stable** libraries
|
||||
are addressed with the highest priority.
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
More Information: [Google Cloud Platform Launch Stages][launch_stages]
|
||||
|
||||
[launch_stages]: https://cloud.google.com/terms/launch-stages
|
||||
|
||||
## Contributing
|
||||
|
||||
Contributions welcome! See the [Contributing Guide](https://github.com/googleapis/nodejs-storage/blob/main/CONTRIBUTING.md).
|
||||
|
||||
Please note that this `README.md`, the `samples/README.md`,
|
||||
and a variety of configuration files in this repository (including `.nycrc` and `tsconfig.json`)
|
||||
are generated from a central template. To edit one of these files, make an edit
|
||||
to its templates in
|
||||
[directory](https://github.com/googleapis/synthtool).
|
||||
|
||||
## License
|
||||
|
||||
Apache Version 2.0
|
||||
|
||||
See [LICENSE](https://github.com/googleapis/nodejs-storage/blob/main/LICENSE)
|
||||
|
||||
[client-docs]: https://googleapis.dev/nodejs/storage/latest
|
||||
[product-docs]: https://cloud.google.com/storage
|
||||
[shell_img]: https://gstatic.com/cloudssh/images/open-btn.png
|
||||
[projects]: https://console.cloud.google.com/project
|
||||
[billing]: https://support.google.com/cloud/answer/6293499#enable-billing
|
||||
[enable_api]: https://console.cloud.google.com/flows/enableapi?apiid=storage-api.googleapis.com
|
||||
[auth]: https://cloud.google.com/docs/authentication/getting-started
|
||||
@ -0,0 +1,151 @@
|
||||
import { BodyResponseCallback, DecorateRequestOptions, Metadata } from './nodejs-common';
|
||||
export interface AclOptions {
|
||||
pathPrefix: string;
|
||||
request: (reqOpts: DecorateRequestOptions, callback: BodyResponseCallback) => void;
|
||||
}
|
||||
export type GetAclResponse = [
|
||||
AccessControlObject | AccessControlObject[],
|
||||
Metadata
|
||||
];
|
||||
export interface GetAclCallback {
|
||||
(err: Error | null, acl?: AccessControlObject | AccessControlObject[] | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export interface GetAclOptions {
|
||||
entity: string;
|
||||
generation?: number;
|
||||
userProject?: string;
|
||||
}
|
||||
export interface UpdateAclOptions {
|
||||
entity: string;
|
||||
role: string;
|
||||
generation?: number;
|
||||
userProject?: string;
|
||||
}
|
||||
export type UpdateAclResponse = [AccessControlObject, Metadata];
|
||||
export interface UpdateAclCallback {
|
||||
(err: Error | null, acl?: AccessControlObject | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export interface AddAclOptions {
|
||||
entity: string;
|
||||
role: string;
|
||||
generation?: number;
|
||||
userProject?: string;
|
||||
}
|
||||
export type AddAclResponse = [AccessControlObject, Metadata];
|
||||
export interface AddAclCallback {
|
||||
(err: Error | null, acl?: AccessControlObject | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export type RemoveAclResponse = [Metadata];
|
||||
export interface RemoveAclCallback {
|
||||
(err: Error | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export interface RemoveAclOptions {
|
||||
entity: string;
|
||||
generation?: number;
|
||||
userProject?: string;
|
||||
}
|
||||
export interface AccessControlObject {
|
||||
entity: string;
|
||||
role: string;
|
||||
projectTeam: string;
|
||||
}
|
||||
/**
|
||||
* Attach functionality to a {@link Storage.acl} instance. This will add an
|
||||
* object for each role group (owners, readers, and writers), with each object
|
||||
* containing methods to add or delete a type of entity.
|
||||
*
|
||||
* As an example, here are a few methods that are created.
|
||||
*
|
||||
* myBucket.acl.readers.deleteGroup('groupId', function(err) {});
|
||||
*
|
||||
* myBucket.acl.owners.addUser('email@example.com', function(err, acl) {});
|
||||
*
|
||||
* myBucket.acl.writers.addDomain('example.com', function(err, acl) {});
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
declare class AclRoleAccessorMethods {
|
||||
private static accessMethods;
|
||||
private static entities;
|
||||
private static roles;
|
||||
owners: {};
|
||||
readers: {};
|
||||
writers: {};
|
||||
constructor();
|
||||
_assignAccessMethods(role: string): void;
|
||||
}
|
||||
/**
|
||||
* Cloud Storage uses access control lists (ACLs) to manage object and
|
||||
* bucket access. ACLs are the mechanism you use to share objects with other
|
||||
* users and allow other users to access your buckets and objects.
|
||||
*
|
||||
* An ACL consists of one or more entries, where each entry grants permissions
|
||||
* to an entity. Permissions define the actions that can be performed against an
|
||||
* object or bucket (for example, `READ` or `WRITE`); the entity defines who the
|
||||
* permission applies to (for example, a specific user or group of users).
|
||||
*
|
||||
* Where an `entity` value is accepted, we follow the format the Cloud Storage
|
||||
* API expects.
|
||||
*
|
||||
* Refer to
|
||||
* https://cloud.google.com/storage/docs/json_api/v1/defaultObjectAccessControls
|
||||
* for the most up-to-date values.
|
||||
*
|
||||
* - `user-userId`
|
||||
* - `user-email`
|
||||
* - `group-groupId`
|
||||
* - `group-email`
|
||||
* - `domain-domain`
|
||||
* - `project-team-projectId`
|
||||
* - `allUsers`
|
||||
* - `allAuthenticatedUsers`
|
||||
*
|
||||
* Examples:
|
||||
*
|
||||
* - The user "liz@example.com" would be `user-liz@example.com`.
|
||||
* - The group "example@googlegroups.com" would be
|
||||
* `group-example@googlegroups.com`.
|
||||
* - To refer to all members of the Google Apps for Business domain
|
||||
* "example.com", the entity would be `domain-example.com`.
|
||||
*
|
||||
* For more detailed information, see
|
||||
* {@link http://goo.gl/6qBBPO| About Access Control Lists}.
|
||||
*
|
||||
* @constructor Acl
|
||||
* @mixin
|
||||
* @param {object} options Configuration options.
|
||||
*/
|
||||
declare class Acl extends AclRoleAccessorMethods {
|
||||
default: Acl;
|
||||
pathPrefix: string;
|
||||
request_: (reqOpts: DecorateRequestOptions, callback: BodyResponseCallback) => void;
|
||||
constructor(options: AclOptions);
|
||||
add(options: AddAclOptions): Promise<AddAclResponse>;
|
||||
add(options: AddAclOptions, callback: AddAclCallback): void;
|
||||
delete(options: RemoveAclOptions): Promise<RemoveAclResponse>;
|
||||
delete(options: RemoveAclOptions, callback: RemoveAclCallback): void;
|
||||
get(options?: GetAclOptions): Promise<GetAclResponse>;
|
||||
get(options: GetAclOptions, callback: GetAclCallback): void;
|
||||
get(callback: GetAclCallback): void;
|
||||
update(options: UpdateAclOptions): Promise<UpdateAclResponse>;
|
||||
update(options: UpdateAclOptions, callback: UpdateAclCallback): void;
|
||||
/**
|
||||
* Transform API responses to a consistent object format.
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
makeAclObject_(accessControlObject: AccessControlObject): AccessControlObject;
|
||||
/**
|
||||
* Patch requests up to the bucket's request object.
|
||||
*
|
||||
* @private
|
||||
*
|
||||
* @param {string} method Action.
|
||||
* @param {string} path Request path.
|
||||
* @param {*} query Request query object.
|
||||
* @param {*} body Request body contents.
|
||||
* @param {function} callback Callback function.
|
||||
*/
|
||||
request(reqOpts: DecorateRequestOptions, callback: BodyResponseCallback): void;
|
||||
}
|
||||
export { Acl, AclRoleAccessorMethods };
|
||||
@ -0,0 +1,719 @@
|
||||
"use strict";
|
||||
// Copyright 2019 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.AclRoleAccessorMethods = exports.Acl = void 0;
|
||||
const promisify_1 = require("@google-cloud/promisify");
|
||||
/**
|
||||
* Attach functionality to a {@link Storage.acl} instance. This will add an
|
||||
* object for each role group (owners, readers, and writers), with each object
|
||||
* containing methods to add or delete a type of entity.
|
||||
*
|
||||
* As an example, here are a few methods that are created.
|
||||
*
|
||||
* myBucket.acl.readers.deleteGroup('groupId', function(err) {});
|
||||
*
|
||||
* myBucket.acl.owners.addUser('email@example.com', function(err, acl) {});
|
||||
*
|
||||
* myBucket.acl.writers.addDomain('example.com', function(err, acl) {});
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
class AclRoleAccessorMethods {
|
||||
constructor() {
|
||||
this.owners = {};
|
||||
this.readers = {};
|
||||
this.writers = {};
|
||||
/**
|
||||
* An object of convenience methods to add or delete owner ACL permissions
|
||||
* for a given entity.
|
||||
*
|
||||
* The supported methods include:
|
||||
*
|
||||
* - `myFile.acl.owners.addAllAuthenticatedUsers`
|
||||
* - `myFile.acl.owners.deleteAllAuthenticatedUsers`
|
||||
* - `myFile.acl.owners.addAllUsers`
|
||||
* - `myFile.acl.owners.deleteAllUsers`
|
||||
* - `myFile.acl.owners.addDomain`
|
||||
* - `myFile.acl.owners.deleteDomain`
|
||||
* - `myFile.acl.owners.addGroup`
|
||||
* - `myFile.acl.owners.deleteGroup`
|
||||
* - `myFile.acl.owners.addProject`
|
||||
* - `myFile.acl.owners.deleteProject`
|
||||
* - `myFile.acl.owners.addUser`
|
||||
* - `myFile.acl.owners.deleteUser`
|
||||
*
|
||||
* @name Acl#owners
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const storage = require('@google-cloud/storage')();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
* const myFile = myBucket.file('my-file');
|
||||
*
|
||||
* //-
|
||||
* // Add a user as an owner of a file.
|
||||
* //-
|
||||
* const myBucket = gcs.bucket('my-bucket');
|
||||
* const myFile = myBucket.file('my-file');
|
||||
* myFile.acl.owners.addUser('email@example.com', function(err, aclObject)
|
||||
* {});
|
||||
*
|
||||
* //-
|
||||
* // For reference, the above command is the same as running the following.
|
||||
* //-
|
||||
* myFile.acl.add({
|
||||
* entity: 'user-email@example.com',
|
||||
* role: gcs.acl.OWNER_ROLE
|
||||
* }, function(err, aclObject) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* myFile.acl.owners.addUser('email@example.com').then(function(data) {
|
||||
* const aclObject = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
this.owners = {};
|
||||
/**
|
||||
* An object of convenience methods to add or delete reader ACL permissions
|
||||
* for a given entity.
|
||||
*
|
||||
* The supported methods include:
|
||||
*
|
||||
* - `myFile.acl.readers.addAllAuthenticatedUsers`
|
||||
* - `myFile.acl.readers.deleteAllAuthenticatedUsers`
|
||||
* - `myFile.acl.readers.addAllUsers`
|
||||
* - `myFile.acl.readers.deleteAllUsers`
|
||||
* - `myFile.acl.readers.addDomain`
|
||||
* - `myFile.acl.readers.deleteDomain`
|
||||
* - `myFile.acl.readers.addGroup`
|
||||
* - `myFile.acl.readers.deleteGroup`
|
||||
* - `myFile.acl.readers.addProject`
|
||||
* - `myFile.acl.readers.deleteProject`
|
||||
* - `myFile.acl.readers.addUser`
|
||||
* - `myFile.acl.readers.deleteUser`
|
||||
*
|
||||
* @name Acl#readers
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const storage = require('@google-cloud/storage')();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
* const myFile = myBucket.file('my-file');
|
||||
*
|
||||
* //-
|
||||
* // Add a user as a reader of a file.
|
||||
* //-
|
||||
* myFile.acl.readers.addUser('email@example.com', function(err, aclObject)
|
||||
* {});
|
||||
*
|
||||
* //-
|
||||
* // For reference, the above command is the same as running the following.
|
||||
* //-
|
||||
* myFile.acl.add({
|
||||
* entity: 'user-email@example.com',
|
||||
* role: gcs.acl.READER_ROLE
|
||||
* }, function(err, aclObject) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* myFile.acl.readers.addUser('email@example.com').then(function(data) {
|
||||
* const aclObject = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
this.readers = {};
|
||||
/**
|
||||
* An object of convenience methods to add or delete writer ACL permissions
|
||||
* for a given entity.
|
||||
*
|
||||
* The supported methods include:
|
||||
*
|
||||
* - `myFile.acl.writers.addAllAuthenticatedUsers`
|
||||
* - `myFile.acl.writers.deleteAllAuthenticatedUsers`
|
||||
* - `myFile.acl.writers.addAllUsers`
|
||||
* - `myFile.acl.writers.deleteAllUsers`
|
||||
* - `myFile.acl.writers.addDomain`
|
||||
* - `myFile.acl.writers.deleteDomain`
|
||||
* - `myFile.acl.writers.addGroup`
|
||||
* - `myFile.acl.writers.deleteGroup`
|
||||
* - `myFile.acl.writers.addProject`
|
||||
* - `myFile.acl.writers.deleteProject`
|
||||
* - `myFile.acl.writers.addUser`
|
||||
* - `myFile.acl.writers.deleteUser`
|
||||
*
|
||||
* @name Acl#writers
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const storage = require('@google-cloud/storage')();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
* const myFile = myBucket.file('my-file');
|
||||
*
|
||||
* //-
|
||||
* // Add a user as a writer of a file.
|
||||
* //-
|
||||
* myFile.acl.writers.addUser('email@example.com', function(err, aclObject)
|
||||
* {});
|
||||
*
|
||||
* //-
|
||||
* // For reference, the above command is the same as running the following.
|
||||
* //-
|
||||
* myFile.acl.add({
|
||||
* entity: 'user-email@example.com',
|
||||
* role: gcs.acl.WRITER_ROLE
|
||||
* }, function(err, aclObject) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* myFile.acl.writers.addUser('email@example.com').then(function(data) {
|
||||
* const aclObject = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
this.writers = {};
|
||||
AclRoleAccessorMethods.roles.forEach(this._assignAccessMethods.bind(this));
|
||||
}
|
||||
_assignAccessMethods(role) {
|
||||
const accessMethods = AclRoleAccessorMethods.accessMethods;
|
||||
const entities = AclRoleAccessorMethods.entities;
|
||||
const roleGroup = role.toLowerCase() + 's';
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
this[roleGroup] = entities.reduce((acc, entity) => {
|
||||
const isPrefix = entity.charAt(entity.length - 1) === '-';
|
||||
accessMethods.forEach(accessMethod => {
|
||||
let method = accessMethod + entity[0].toUpperCase() + entity.substring(1);
|
||||
if (isPrefix) {
|
||||
method = method.replace('-', '');
|
||||
}
|
||||
// Wrap the parent accessor method (e.g. `add` or `delete`) to avoid the
|
||||
// more complex API of specifying an `entity` and `role`.
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
acc[method] = (entityId, options, callback) => {
|
||||
let apiEntity;
|
||||
if (typeof options === 'function') {
|
||||
callback = options;
|
||||
options = {};
|
||||
}
|
||||
if (isPrefix) {
|
||||
apiEntity = entity + entityId;
|
||||
}
|
||||
else {
|
||||
// If the entity is not a prefix, it is a special entity group
|
||||
// that does not require further details. The accessor methods
|
||||
// only accept a callback.
|
||||
apiEntity = entity;
|
||||
callback = entityId;
|
||||
}
|
||||
options = Object.assign({
|
||||
entity: apiEntity,
|
||||
role,
|
||||
}, options);
|
||||
const args = [options];
|
||||
if (typeof callback === 'function') {
|
||||
args.push(callback);
|
||||
}
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
return this[accessMethod].apply(this, args);
|
||||
};
|
||||
});
|
||||
return acc;
|
||||
}, {});
|
||||
}
|
||||
}
|
||||
exports.AclRoleAccessorMethods = AclRoleAccessorMethods;
|
||||
AclRoleAccessorMethods.accessMethods = ['add', 'delete'];
|
||||
AclRoleAccessorMethods.entities = [
|
||||
// Special entity groups that do not require further specification.
|
||||
'allAuthenticatedUsers',
|
||||
'allUsers',
|
||||
// Entity groups that require specification, e.g. `user-email@example.com`.
|
||||
'domain-',
|
||||
'group-',
|
||||
'project-',
|
||||
'user-',
|
||||
];
|
||||
AclRoleAccessorMethods.roles = ['OWNER', 'READER', 'WRITER'];
|
||||
/**
|
||||
* Cloud Storage uses access control lists (ACLs) to manage object and
|
||||
* bucket access. ACLs are the mechanism you use to share objects with other
|
||||
* users and allow other users to access your buckets and objects.
|
||||
*
|
||||
* An ACL consists of one or more entries, where each entry grants permissions
|
||||
* to an entity. Permissions define the actions that can be performed against an
|
||||
* object or bucket (for example, `READ` or `WRITE`); the entity defines who the
|
||||
* permission applies to (for example, a specific user or group of users).
|
||||
*
|
||||
* Where an `entity` value is accepted, we follow the format the Cloud Storage
|
||||
* API expects.
|
||||
*
|
||||
* Refer to
|
||||
* https://cloud.google.com/storage/docs/json_api/v1/defaultObjectAccessControls
|
||||
* for the most up-to-date values.
|
||||
*
|
||||
* - `user-userId`
|
||||
* - `user-email`
|
||||
* - `group-groupId`
|
||||
* - `group-email`
|
||||
* - `domain-domain`
|
||||
* - `project-team-projectId`
|
||||
* - `allUsers`
|
||||
* - `allAuthenticatedUsers`
|
||||
*
|
||||
* Examples:
|
||||
*
|
||||
* - The user "liz@example.com" would be `user-liz@example.com`.
|
||||
* - The group "example@googlegroups.com" would be
|
||||
* `group-example@googlegroups.com`.
|
||||
* - To refer to all members of the Google Apps for Business domain
|
||||
* "example.com", the entity would be `domain-example.com`.
|
||||
*
|
||||
* For more detailed information, see
|
||||
* {@link http://goo.gl/6qBBPO| About Access Control Lists}.
|
||||
*
|
||||
* @constructor Acl
|
||||
* @mixin
|
||||
* @param {object} options Configuration options.
|
||||
*/
|
||||
class Acl extends AclRoleAccessorMethods {
|
||||
constructor(options) {
|
||||
super();
|
||||
this.pathPrefix = options.pathPrefix;
|
||||
this.request_ = options.request;
|
||||
}
|
||||
/**
|
||||
* @typedef {array} AddAclResponse
|
||||
* @property {object} 0 The Acl Objects.
|
||||
* @property {object} 1 The full API response.
|
||||
*/
|
||||
/**
|
||||
* @callback AddAclCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {object} acl The Acl Objects.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
/**
|
||||
* Add access controls on a {@link Bucket} or {@link File}.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/bucketAccessControls/insert| BucketAccessControls: insert API Documentation}
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/objectAccessControls/insert| ObjectAccessControls: insert API Documentation}
|
||||
*
|
||||
* @param {object} options Configuration options.
|
||||
* @param {string} options.entity Whose permissions will be added.
|
||||
* @param {string} options.role Permissions allowed for the defined entity.
|
||||
* See {@link https://cloud.google.com/storage/docs/access-control Access
|
||||
* Control}.
|
||||
* @param {number} [options.generation] **File Objects Only** Select a specific
|
||||
* revision of this file (as opposed to the latest version, the default).
|
||||
* @param {string} [options.userProject] The ID of the project which will be
|
||||
* billed for the request.
|
||||
* @param {AddAclCallback} [callback] Callback function.
|
||||
* @returns {Promise<AddAclResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const storage = require('@google-cloud/storage')();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
* const myFile = myBucket.file('my-file');
|
||||
*
|
||||
* const options = {
|
||||
* entity: 'user-useremail@example.com',
|
||||
* role: gcs.acl.OWNER_ROLE
|
||||
* };
|
||||
*
|
||||
* myBucket.acl.add(options, function(err, aclObject, apiResponse) {});
|
||||
*
|
||||
* //-
|
||||
* // For file ACL operations, you can also specify a `generation` property.
|
||||
* // Here is how you would grant ownership permissions to a user on a
|
||||
* specific
|
||||
* // revision of a file.
|
||||
* //-
|
||||
* myFile.acl.add({
|
||||
* entity: 'user-useremail@example.com',
|
||||
* role: gcs.acl.OWNER_ROLE,
|
||||
* generation: 1
|
||||
* }, function(err, aclObject, apiResponse) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* myBucket.acl.add(options).then(function(data) {
|
||||
* const aclObject = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
*
|
||||
* ```
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_add_file_owner
|
||||
* Example of adding an owner to a file:
|
||||
*
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_add_bucket_owner
|
||||
* Example of adding an owner to a bucket:
|
||||
*
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_add_bucket_default_owner
|
||||
* Example of adding a default owner to a bucket:
|
||||
*/
|
||||
add(options, callback) {
|
||||
const query = {};
|
||||
if (options.generation) {
|
||||
query.generation = options.generation;
|
||||
}
|
||||
if (options.userProject) {
|
||||
query.userProject = options.userProject;
|
||||
}
|
||||
this.request({
|
||||
method: 'POST',
|
||||
uri: '',
|
||||
qs: query,
|
||||
maxRetries: 0,
|
||||
json: {
|
||||
entity: options.entity,
|
||||
role: options.role.toUpperCase(),
|
||||
},
|
||||
}, (err, resp) => {
|
||||
if (err) {
|
||||
callback(err, null, resp);
|
||||
return;
|
||||
}
|
||||
callback(null, this.makeAclObject_(resp), resp);
|
||||
});
|
||||
}
|
||||
/**
|
||||
* @typedef {array} RemoveAclResponse
|
||||
* @property {object} 0 The full API response.
|
||||
*/
|
||||
/**
|
||||
* @callback RemoveAclCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
/**
|
||||
* Delete access controls on a {@link Bucket} or {@link File}.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/bucketAccessControls/delete| BucketAccessControls: delete API Documentation}
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/objectAccessControls/delete| ObjectAccessControls: delete API Documentation}
|
||||
*
|
||||
* @param {object} options Configuration object.
|
||||
* @param {string} options.entity Whose permissions will be revoked.
|
||||
* @param {int} [options.generation] **File Objects Only** Select a specific
|
||||
* revision of this file (as opposed to the latest version, the default).
|
||||
* @param {string} [options.userProject] The ID of the project which will be
|
||||
* billed for the request.
|
||||
* @param {RemoveAclCallback} callback The callback function.
|
||||
* @returns {Promise<RemoveAclResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const storage = require('@google-cloud/storage')();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
* const myFile = myBucket.file('my-file');
|
||||
*
|
||||
* myBucket.acl.delete({
|
||||
* entity: 'user-useremail@example.com'
|
||||
* }, function(err, apiResponse) {});
|
||||
*
|
||||
* //-
|
||||
* // For file ACL operations, you can also specify a `generation` property.
|
||||
* //-
|
||||
* myFile.acl.delete({
|
||||
* entity: 'user-useremail@example.com',
|
||||
* generation: 1
|
||||
* }, function(err, apiResponse) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* myFile.acl.delete().then(function(data) {
|
||||
* const apiResponse = data[0];
|
||||
* });
|
||||
*
|
||||
* ```
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_remove_bucket_owner
|
||||
* Example of removing an owner from a bucket:
|
||||
*
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_remove_bucket_default_owner
|
||||
* Example of removing a default owner from a bucket:
|
||||
*
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_remove_file_owner
|
||||
* Example of removing an owner from a bucket:
|
||||
*/
|
||||
delete(options, callback) {
|
||||
const query = {};
|
||||
if (options.generation) {
|
||||
query.generation = options.generation;
|
||||
}
|
||||
if (options.userProject) {
|
||||
query.userProject = options.userProject;
|
||||
}
|
||||
this.request({
|
||||
method: 'DELETE',
|
||||
uri: '/' + encodeURIComponent(options.entity),
|
||||
qs: query,
|
||||
}, (err, resp) => {
|
||||
callback(err, resp);
|
||||
});
|
||||
}
|
||||
/**
|
||||
* @typedef {array} GetAclResponse
|
||||
* @property {object|object[]} 0 Single or array of Acl Objects.
|
||||
* @property {object} 1 The full API response.
|
||||
*/
|
||||
/**
|
||||
* @callback GetAclCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {object|object[]} acl Single or array of Acl Objects.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
/**
|
||||
* Get access controls on a {@link Bucket} or {@link File}. If
|
||||
* an entity is omitted, you will receive an array of all applicable access
|
||||
* controls.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/bucketAccessControls/get| BucketAccessControls: get API Documentation}
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/objectAccessControls/get| ObjectAccessControls: get API Documentation}
|
||||
*
|
||||
* @param {object|function} [options] Configuration options. If you want to
|
||||
* receive a list of all access controls, pass the callback function as
|
||||
* the only argument.
|
||||
* @param {string} options.entity Whose permissions will be fetched.
|
||||
* @param {number} [options.generation] **File Objects Only** Select a specific
|
||||
* revision of this file (as opposed to the latest version, the default).
|
||||
* @param {string} [options.userProject] The ID of the project which will be
|
||||
* billed for the request.
|
||||
* @param {GetAclCallback} [callback] Callback function.
|
||||
* @returns {Promise<GetAclResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const storage = require('@google-cloud/storage')();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
* const myFile = myBucket.file('my-file');
|
||||
*
|
||||
* myBucket.acl.get({
|
||||
* entity: 'user-useremail@example.com'
|
||||
* }, function(err, aclObject, apiResponse) {});
|
||||
*
|
||||
* //-
|
||||
* // Get all access controls.
|
||||
* //-
|
||||
* myBucket.acl.get(function(err, aclObjects, apiResponse) {
|
||||
* // aclObjects = [
|
||||
* // {
|
||||
* // entity: 'user-useremail@example.com',
|
||||
* // role: 'owner'
|
||||
* // }
|
||||
* // ]
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // For file ACL operations, you can also specify a `generation` property.
|
||||
* //-
|
||||
* myFile.acl.get({
|
||||
* entity: 'user-useremail@example.com',
|
||||
* generation: 1
|
||||
* }, function(err, aclObject, apiResponse) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* myBucket.acl.get().then(function(data) {
|
||||
* const aclObject = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
*
|
||||
* ```
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_print_file_acl
|
||||
* Example of printing a file's ACL:
|
||||
*
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_print_file_acl_for_user
|
||||
* Example of printing a file's ACL for a specific user:
|
||||
*
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_print_bucket_acl
|
||||
* Example of printing a bucket's ACL:
|
||||
*
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_print_bucket_acl_for_user
|
||||
* Example of printing a bucket's ACL for a specific user:
|
||||
*/
|
||||
get(optionsOrCallback, cb) {
|
||||
const options = typeof optionsOrCallback === 'object' ? optionsOrCallback : null;
|
||||
const callback = typeof optionsOrCallback === 'function' ? optionsOrCallback : cb;
|
||||
let path = '';
|
||||
const query = {};
|
||||
if (options) {
|
||||
path = '/' + encodeURIComponent(options.entity);
|
||||
if (options.generation) {
|
||||
query.generation = options.generation;
|
||||
}
|
||||
if (options.userProject) {
|
||||
query.userProject = options.userProject;
|
||||
}
|
||||
}
|
||||
this.request({
|
||||
uri: path,
|
||||
qs: query,
|
||||
}, (err, resp) => {
|
||||
if (err) {
|
||||
callback(err, null, resp);
|
||||
return;
|
||||
}
|
||||
let results;
|
||||
if (resp.items) {
|
||||
results = resp.items.map(this.makeAclObject_);
|
||||
}
|
||||
else {
|
||||
results = this.makeAclObject_(resp);
|
||||
}
|
||||
callback(null, results, resp);
|
||||
});
|
||||
}
|
||||
/**
|
||||
* @typedef {array} UpdateAclResponse
|
||||
* @property {object} 0 The updated Acl Objects.
|
||||
* @property {object} 1 The full API response.
|
||||
*/
|
||||
/**
|
||||
* @callback UpdateAclCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {object} acl The updated Acl Objects.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
/**
|
||||
* Update access controls on a {@link Bucket} or {@link File}.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/bucketAccessControls/update| BucketAccessControls: update API Documentation}
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/objectAccessControls/update| ObjectAccessControls: update API Documentation}
|
||||
*
|
||||
* @param {object} options Configuration options.
|
||||
* @param {string} options.entity Whose permissions will be updated.
|
||||
* @param {string} options.role Permissions allowed for the defined entity.
|
||||
* See {@link Storage.acl}.
|
||||
* @param {number} [options.generation] **File Objects Only** Select a specific
|
||||
* revision of this file (as opposed to the latest version, the default).
|
||||
* @param {string} [options.userProject] The ID of the project which will be
|
||||
* billed for the request.
|
||||
* @param {UpdateAclCallback} [callback] Callback function.
|
||||
* @returns {Promise<UpdateAclResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const storage = require('@google-cloud/storage')();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
* const myFile = myBucket.file('my-file');
|
||||
*
|
||||
* const options = {
|
||||
* entity: 'user-useremail@example.com',
|
||||
* role: gcs.acl.WRITER_ROLE
|
||||
* };
|
||||
*
|
||||
* myBucket.acl.update(options, function(err, aclObject, apiResponse) {});
|
||||
*
|
||||
* //-
|
||||
* // For file ACL operations, you can also specify a `generation` property.
|
||||
* //-
|
||||
* myFile.acl.update({
|
||||
* entity: 'user-useremail@example.com',
|
||||
* role: gcs.acl.WRITER_ROLE,
|
||||
* generation: 1
|
||||
* }, function(err, aclObject, apiResponse) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* myFile.acl.update(options).then(function(data) {
|
||||
* const aclObject = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
update(options, callback) {
|
||||
const query = {};
|
||||
if (options.generation) {
|
||||
query.generation = options.generation;
|
||||
}
|
||||
if (options.userProject) {
|
||||
query.userProject = options.userProject;
|
||||
}
|
||||
this.request({
|
||||
method: 'PUT',
|
||||
uri: '/' + encodeURIComponent(options.entity),
|
||||
qs: query,
|
||||
json: {
|
||||
role: options.role.toUpperCase(),
|
||||
},
|
||||
}, (err, resp) => {
|
||||
if (err) {
|
||||
callback(err, null, resp);
|
||||
return;
|
||||
}
|
||||
callback(null, this.makeAclObject_(resp), resp);
|
||||
});
|
||||
}
|
||||
/**
|
||||
* Transform API responses to a consistent object format.
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
makeAclObject_(accessControlObject) {
|
||||
const obj = {
|
||||
entity: accessControlObject.entity,
|
||||
role: accessControlObject.role,
|
||||
};
|
||||
if (accessControlObject.projectTeam) {
|
||||
obj.projectTeam = accessControlObject.projectTeam;
|
||||
}
|
||||
return obj;
|
||||
}
|
||||
/**
|
||||
* Patch requests up to the bucket's request object.
|
||||
*
|
||||
* @private
|
||||
*
|
||||
* @param {string} method Action.
|
||||
* @param {string} path Request path.
|
||||
* @param {*} query Request query object.
|
||||
* @param {*} body Request body contents.
|
||||
* @param {function} callback Callback function.
|
||||
*/
|
||||
request(reqOpts, callback) {
|
||||
reqOpts.uri = this.pathPrefix + reqOpts.uri;
|
||||
this.request_(reqOpts, callback);
|
||||
}
|
||||
}
|
||||
exports.Acl = Acl;
|
||||
/*! Developer Documentation
|
||||
*
|
||||
* All async methods (except for streams) will return a Promise in the event
|
||||
* that a callback is omitted.
|
||||
*/
|
||||
(0, promisify_1.promisifyAll)(Acl, {
|
||||
exclude: ['request'],
|
||||
});
|
||||
//# sourceMappingURL=acl.js.map
|
||||
@ -0,0 +1,701 @@
|
||||
/// <reference types="node" />
|
||||
/// <reference types="node" />
|
||||
/// <reference types="node" />
|
||||
/// <reference types="node" />
|
||||
import { ApiError, BodyResponseCallback, DecorateRequestOptions, DeleteCallback, ExistsCallback, GetConfig, Metadata, MetadataCallback, ResponseBody, ServiceObject, SetMetadataResponse } from './nodejs-common';
|
||||
import * as http from 'http';
|
||||
import { Acl } from './acl';
|
||||
import { Channel } from './channel';
|
||||
import { File, FileOptions, CreateResumableUploadOptions, CreateWriteStreamOptions } from './file';
|
||||
import { Iam } from './iam';
|
||||
import { Notification } from './notification';
|
||||
import { Storage, Cors, PreconditionOptions, BucketOptions } from './storage';
|
||||
import { GetSignedUrlResponse, GetSignedUrlCallback, URLSigner, Query } from './signer';
|
||||
import { Readable } from 'stream';
|
||||
import { CRC32CValidatorGenerator } from './crc32c';
|
||||
import { URL } from 'url';
|
||||
import { SetMetadataOptions } from './nodejs-common/service-object';
|
||||
export type GetFilesResponse = [File[], {}, Metadata];
|
||||
export interface GetFilesCallback {
|
||||
(err: Error | null, files?: File[], nextQuery?: {}, apiResponse?: Metadata): void;
|
||||
}
|
||||
interface WatchAllOptions {
|
||||
delimiter?: string;
|
||||
maxResults?: number;
|
||||
pageToken?: string;
|
||||
prefix?: string;
|
||||
projection?: string;
|
||||
userProject?: string;
|
||||
versions?: boolean;
|
||||
}
|
||||
export interface AddLifecycleRuleOptions extends PreconditionOptions {
|
||||
append?: boolean;
|
||||
}
|
||||
export interface LifecycleRule {
|
||||
action: {
|
||||
type: string;
|
||||
storageClass?: string;
|
||||
} | string;
|
||||
condition: {
|
||||
[key: string]: boolean | Date | number | string | string[];
|
||||
};
|
||||
storageClass?: string;
|
||||
}
|
||||
export interface EnableLoggingOptions extends PreconditionOptions {
|
||||
bucket?: string | Bucket;
|
||||
prefix: string;
|
||||
}
|
||||
export interface GetFilesOptions {
|
||||
autoPaginate?: boolean;
|
||||
delimiter?: string;
|
||||
endOffset?: string;
|
||||
includeTrailingDelimiter?: boolean;
|
||||
prefix?: string;
|
||||
maxApiCalls?: number;
|
||||
maxResults?: number;
|
||||
pageToken?: string;
|
||||
startOffset?: string;
|
||||
userProject?: string;
|
||||
versions?: boolean;
|
||||
}
|
||||
export interface CombineOptions extends PreconditionOptions {
|
||||
kmsKeyName?: string;
|
||||
userProject?: string;
|
||||
}
|
||||
export interface CombineCallback {
|
||||
(err: Error | null, newFile: File | null, apiResponse: Metadata): void;
|
||||
}
|
||||
export type CombineResponse = [File, Metadata];
|
||||
export interface CreateChannelConfig extends WatchAllOptions {
|
||||
address: string;
|
||||
}
|
||||
export interface CreateChannelOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export type CreateChannelResponse = [Channel, Metadata];
|
||||
export interface CreateChannelCallback {
|
||||
(err: Error | null, channel: Channel | null, apiResponse: Metadata): void;
|
||||
}
|
||||
export interface CreateNotificationOptions {
|
||||
customAttributes?: {
|
||||
[key: string]: string;
|
||||
};
|
||||
eventTypes?: string[];
|
||||
objectNamePrefix?: string;
|
||||
payloadFormat?: string;
|
||||
userProject?: string;
|
||||
}
|
||||
export interface CreateNotificationCallback {
|
||||
(err: Error | null, notification: Notification | null, apiResponse: Metadata): void;
|
||||
}
|
||||
export type CreateNotificationResponse = [Notification, Metadata];
|
||||
export interface DeleteBucketOptions {
|
||||
ignoreNotFound?: boolean;
|
||||
userProject?: string;
|
||||
}
|
||||
export type DeleteBucketResponse = [Metadata];
|
||||
export interface DeleteBucketCallback extends DeleteCallback {
|
||||
(err: Error | null, apiResponse: Metadata): void;
|
||||
}
|
||||
export interface DeleteFilesOptions extends GetFilesOptions, PreconditionOptions {
|
||||
force?: boolean;
|
||||
}
|
||||
export interface DeleteFilesCallback {
|
||||
(err: Error | Error[] | null, apiResponse?: object): void;
|
||||
}
|
||||
export type DeleteLabelsResponse = [Metadata];
|
||||
export type DeleteLabelsCallback = SetLabelsCallback;
|
||||
export type DeleteLabelsOptions = PreconditionOptions;
|
||||
export type DisableRequesterPaysOptions = PreconditionOptions;
|
||||
export type DisableRequesterPaysResponse = [Metadata];
|
||||
export interface DisableRequesterPaysCallback {
|
||||
(err?: Error | null, apiResponse?: object): void;
|
||||
}
|
||||
export type EnableRequesterPaysResponse = [Metadata];
|
||||
export interface EnableRequesterPaysCallback {
|
||||
(err?: Error | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export type EnableRequesterPaysOptions = PreconditionOptions;
|
||||
export interface BucketExistsOptions extends GetConfig {
|
||||
userProject?: string;
|
||||
}
|
||||
export type BucketExistsResponse = [boolean];
|
||||
export type BucketExistsCallback = ExistsCallback;
|
||||
export interface GetBucketOptions extends GetConfig {
|
||||
userProject?: string;
|
||||
}
|
||||
export type GetBucketResponse = [Bucket, Metadata];
|
||||
export interface GetBucketCallback {
|
||||
(err: ApiError | null, bucket: Bucket | null, apiResponse: Metadata): void;
|
||||
}
|
||||
export interface GetLabelsOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export type GetLabelsResponse = [Metadata];
|
||||
export interface GetLabelsCallback {
|
||||
(err: Error | null, labels: object | null): void;
|
||||
}
|
||||
export type GetBucketMetadataResponse = [Metadata, Metadata];
|
||||
export interface GetBucketMetadataCallback {
|
||||
(err: ApiError | null, metadata: Metadata | null, apiResponse: Metadata): void;
|
||||
}
|
||||
export interface GetBucketMetadataOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export interface GetBucketSignedUrlConfig {
|
||||
action: 'list';
|
||||
version?: 'v2' | 'v4';
|
||||
cname?: string;
|
||||
virtualHostedStyle?: boolean;
|
||||
expires: string | number | Date;
|
||||
extensionHeaders?: http.OutgoingHttpHeaders;
|
||||
queryParams?: Query;
|
||||
}
|
||||
export declare enum BucketActionToHTTPMethod {
|
||||
list = "GET"
|
||||
}
|
||||
export declare enum AvailableServiceObjectMethods {
|
||||
setMetadata = 0,
|
||||
delete = 1
|
||||
}
|
||||
export interface GetNotificationsOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export interface GetNotificationsCallback {
|
||||
(err: Error | null, notifications: Notification[] | null, apiResponse: Metadata): void;
|
||||
}
|
||||
export type GetNotificationsResponse = [Notification[], Metadata];
|
||||
export interface MakeBucketPrivateOptions {
|
||||
includeFiles?: boolean;
|
||||
force?: boolean;
|
||||
metadata?: Metadata;
|
||||
userProject?: string;
|
||||
preconditionOpts?: PreconditionOptions;
|
||||
}
|
||||
export type MakeBucketPrivateResponse = [File[]];
|
||||
export interface MakeBucketPrivateCallback {
|
||||
(err?: Error | null, files?: File[]): void;
|
||||
}
|
||||
export interface MakeBucketPublicOptions {
|
||||
includeFiles?: boolean;
|
||||
force?: boolean;
|
||||
}
|
||||
export interface MakeBucketPublicCallback {
|
||||
(err?: Error | null, files?: File[]): void;
|
||||
}
|
||||
export type MakeBucketPublicResponse = [File[]];
|
||||
export interface SetBucketMetadataOptions extends PreconditionOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export type SetBucketMetadataResponse = [Metadata];
|
||||
export interface SetBucketMetadataCallback {
|
||||
(err?: Error | null, metadata?: Metadata): void;
|
||||
}
|
||||
export interface BucketLockCallback {
|
||||
(err?: Error | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export type BucketLockResponse = [Metadata];
|
||||
export interface Labels {
|
||||
[key: string]: string;
|
||||
}
|
||||
export interface SetLabelsOptions extends PreconditionOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export type SetLabelsResponse = [Metadata];
|
||||
export interface SetLabelsCallback {
|
||||
(err?: Error | null, metadata?: Metadata): void;
|
||||
}
|
||||
export interface SetBucketStorageClassOptions extends PreconditionOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export interface SetBucketStorageClassCallback {
|
||||
(err?: Error | null): void;
|
||||
}
|
||||
export type UploadResponse = [File, Metadata];
|
||||
export interface UploadCallback {
|
||||
(err: Error | null, file?: File | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export interface UploadOptions extends CreateResumableUploadOptions, CreateWriteStreamOptions {
|
||||
destination?: string | File;
|
||||
encryptionKey?: string | Buffer;
|
||||
kmsKeyName?: string;
|
||||
onUploadProgress?: (progressEvent: any) => void;
|
||||
}
|
||||
export interface MakeAllFilesPublicPrivateOptions {
|
||||
force?: boolean;
|
||||
private?: boolean;
|
||||
public?: boolean;
|
||||
userProject?: string;
|
||||
}
|
||||
interface MakeAllFilesPublicPrivateCallback {
|
||||
(err?: Error | Error[] | null, files?: File[]): void;
|
||||
}
|
||||
type MakeAllFilesPublicPrivateResponse = [File[]];
|
||||
export declare enum BucketExceptionMessages {
|
||||
PROVIDE_SOURCE_FILE = "You must provide at least one source file.",
|
||||
DESTINATION_FILE_NOT_SPECIFIED = "A destination file must be specified.",
|
||||
CHANNEL_ID_REQUIRED = "An ID is required to create a channel.",
|
||||
CHANNEL_ADDRESS_REQUIRED = "An address is required to create a channel.",
|
||||
TOPIC_NAME_REQUIRED = "A valid topic name is required.",
|
||||
CONFIGURATION_OBJECT_PREFIX_REQUIRED = "A configuration object with a prefix is required.",
|
||||
SPECIFY_FILE_NAME = "A file name must be specified.",
|
||||
METAGENERATION_NOT_PROVIDED = "A metageneration must be provided.",
|
||||
SUPPLY_NOTIFICATION_ID = "You must supply a notification ID."
|
||||
}
|
||||
/**
|
||||
* @callback Crc32cGeneratorToStringCallback
|
||||
* A method returning the CRC32C as a base64-encoded string.
|
||||
*
|
||||
* @returns {string}
|
||||
*
|
||||
* @example
|
||||
* Hashing the string 'data' should return 'rth90Q=='
|
||||
*
|
||||
* ```js
|
||||
* const buffer = Buffer.from('data');
|
||||
* crc32c.update(buffer);
|
||||
* crc32c.toString(); // 'rth90Q=='
|
||||
* ```
|
||||
**/
|
||||
/**
|
||||
* @callback Crc32cGeneratorValidateCallback
|
||||
* A method validating a base64-encoded CRC32C string.
|
||||
*
|
||||
* @param {string} [value] base64-encoded CRC32C string to validate
|
||||
* @returns {boolean}
|
||||
*
|
||||
* @example
|
||||
* Should return `true` if the value matches, `false` otherwise
|
||||
*
|
||||
* ```js
|
||||
* const buffer = Buffer.from('data');
|
||||
* crc32c.update(buffer);
|
||||
* crc32c.validate('DkjKuA=='); // false
|
||||
* crc32c.validate('rth90Q=='); // true
|
||||
* ```
|
||||
**/
|
||||
/**
|
||||
* @callback Crc32cGeneratorUpdateCallback
|
||||
* A method for passing `Buffer`s for CRC32C generation.
|
||||
*
|
||||
* @param {Buffer} [data] data to update CRC32C value with
|
||||
* @returns {undefined}
|
||||
*
|
||||
* @example
|
||||
* Hashing buffers from 'some ' and 'text\n'
|
||||
*
|
||||
* ```js
|
||||
* const buffer1 = Buffer.from('some ');
|
||||
* crc32c.update(buffer1);
|
||||
*
|
||||
* const buffer2 = Buffer.from('text\n');
|
||||
* crc32c.update(buffer2);
|
||||
*
|
||||
* crc32c.toString(); // 'DkjKuA=='
|
||||
* ```
|
||||
**/
|
||||
/**
|
||||
* @typedef {object} CRC32CValidator
|
||||
* @property {Crc32cGeneratorToStringCallback}
|
||||
* @property {Crc32cGeneratorValidateCallback}
|
||||
* @property {Crc32cGeneratorUpdateCallback}
|
||||
*/
|
||||
/**
|
||||
* A function that generates a CRC32C Validator. Defaults to {@link CRC32C}
|
||||
*
|
||||
* @name Bucket#crc32cGenerator
|
||||
* @type {CRC32CValidator}
|
||||
*/
|
||||
/**
|
||||
* Get and set IAM policies for your bucket.
|
||||
*
|
||||
* @name Bucket#iam
|
||||
* @mixes Iam
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/access-control/iam#short_title_iam_management| Cloud Storage IAM Management}
|
||||
* See {@link https://cloud.google.com/iam/docs/granting-changing-revoking-access| Granting, Changing, and Revoking Access}
|
||||
* See {@link https://cloud.google.com/iam/docs/understanding-roles| IAM Roles}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('albums');
|
||||
*
|
||||
* //-
|
||||
* // Get the IAM policy for your bucket.
|
||||
* //-
|
||||
* bucket.iam.getPolicy(function(err, policy) {
|
||||
* console.log(policy);
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* bucket.iam.getPolicy().then(function(data) {
|
||||
* const policy = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
*
|
||||
* ```
|
||||
* @example <caption>include:samples/iam.js</caption>
|
||||
* region_tag:storage_view_bucket_iam_members
|
||||
* Example of retrieving a bucket's IAM policy:
|
||||
*
|
||||
* @example <caption>include:samples/iam.js</caption>
|
||||
* region_tag:storage_add_bucket_iam_member
|
||||
* Example of adding to a bucket's IAM policy:
|
||||
*
|
||||
* @example <caption>include:samples/iam.js</caption>
|
||||
* region_tag:storage_remove_bucket_iam_member
|
||||
* Example of removing from a bucket's IAM policy:
|
||||
*/
|
||||
/**
|
||||
* Cloud Storage uses access control lists (ACLs) to manage object and
|
||||
* bucket access. ACLs are the mechanism you use to share objects with other
|
||||
* users and allow other users to access your buckets and objects.
|
||||
*
|
||||
* An ACL consists of one or more entries, where each entry grants permissions
|
||||
* to an entity. Permissions define the actions that can be performed against
|
||||
* an object or bucket (for example, `READ` or `WRITE`); the entity defines
|
||||
* who the permission applies to (for example, a specific user or group of
|
||||
* users).
|
||||
*
|
||||
* The `acl` object on a Bucket instance provides methods to get you a list of
|
||||
* the ACLs defined on your bucket, as well as set, update, and delete them.
|
||||
*
|
||||
* Buckets also have
|
||||
* {@link https://cloud.google.com/storage/docs/access-control/lists#default| default ACLs}
|
||||
* for all created files. Default ACLs specify permissions that all new
|
||||
* objects added to the bucket will inherit by default. You can add, delete,
|
||||
* get, and update entities and permissions for these as well with
|
||||
* {@link Bucket#acl.default}.
|
||||
*
|
||||
* See {@link http://goo.gl/6qBBPO| About Access Control Lists}
|
||||
* See {@link https://cloud.google.com/storage/docs/access-control/lists#default| Default ACLs}
|
||||
*
|
||||
* @name Bucket#acl
|
||||
* @mixes Acl
|
||||
* @property {Acl} default Cloud Storage Buckets have
|
||||
* {@link https://cloud.google.com/storage/docs/access-control/lists#default| default ACLs}
|
||||
* for all created files. You can add, delete, get, and update entities and
|
||||
* permissions for these as well. The method signatures and examples are all
|
||||
* the same, after only prefixing the method call with `default`.
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
*
|
||||
* //-
|
||||
* // Make a bucket's contents publicly readable.
|
||||
* //-
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
*
|
||||
* const options = {
|
||||
* entity: 'allUsers',
|
||||
* role: storage.acl.READER_ROLE
|
||||
* };
|
||||
*
|
||||
* myBucket.acl.add(options, function(err, aclObject) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* myBucket.acl.add(options).then(function(data) {
|
||||
* const aclObject = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
*
|
||||
* ```
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_print_bucket_acl
|
||||
* Example of printing a bucket's ACL:
|
||||
*
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_print_bucket_acl_for_user
|
||||
* Example of printing a bucket's ACL for a specific user:
|
||||
*
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_add_bucket_owner
|
||||
* Example of adding an owner to a bucket:
|
||||
*
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_remove_bucket_owner
|
||||
* Example of removing an owner from a bucket:
|
||||
*
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_add_bucket_default_owner
|
||||
* Example of adding a default owner to a bucket:
|
||||
*
|
||||
* @example <caption>include:samples/acl.js</caption>
|
||||
* region_tag:storage_remove_bucket_default_owner
|
||||
* Example of removing a default owner from a bucket:
|
||||
*/
|
||||
/**
|
||||
* The API-formatted resource description of the bucket.
|
||||
*
|
||||
* Note: This is not guaranteed to be up-to-date when accessed. To get the
|
||||
* latest record, call the `getMetadata()` method.
|
||||
*
|
||||
* @name Bucket#metadata
|
||||
* @type {object}
|
||||
*/
|
||||
/**
|
||||
* The bucket's name.
|
||||
* @name Bucket#name
|
||||
* @type {string}
|
||||
*/
|
||||
/**
|
||||
* Get {@link File} objects for the files currently in the bucket as a
|
||||
* readable object stream.
|
||||
*
|
||||
* @method Bucket#getFilesStream
|
||||
* @param {GetFilesOptions} [query] Query object for listing files.
|
||||
* @returns {ReadableStream} A readable stream that emits {@link File} instances.
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('albums');
|
||||
*
|
||||
* bucket.getFilesStream()
|
||||
* .on('error', console.error)
|
||||
* .on('data', function(file) {
|
||||
* // file is a File object.
|
||||
* })
|
||||
* .on('end', function() {
|
||||
* // All files retrieved.
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If you anticipate many results, you can end a stream early to prevent
|
||||
* // unnecessary processing and API requests.
|
||||
* //-
|
||||
* bucket.getFilesStream()
|
||||
* .on('data', function(file) {
|
||||
* this.end();
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If you're filtering files with a delimiter, you should use
|
||||
* // {@link Bucket#getFiles} and set `autoPaginate: false` in order to
|
||||
* // preserve the `apiResponse` argument.
|
||||
* //-
|
||||
* const prefixes = [];
|
||||
*
|
||||
* function callback(err, files, nextQuery, apiResponse) {
|
||||
* prefixes = prefixes.concat(apiResponse.prefixes);
|
||||
*
|
||||
* if (nextQuery) {
|
||||
* bucket.getFiles(nextQuery, callback);
|
||||
* } else {
|
||||
* // prefixes = The finished array of prefixes.
|
||||
* }
|
||||
* }
|
||||
*
|
||||
* bucket.getFiles({
|
||||
* autoPaginate: false,
|
||||
* delimiter: '/'
|
||||
* }, callback);
|
||||
* ```
|
||||
*/
|
||||
/**
|
||||
* Create a Bucket object to interact with a Cloud Storage bucket.
|
||||
*
|
||||
* @class
|
||||
* @hideconstructor
|
||||
*
|
||||
* @param {Storage} storage A {@link Storage} instance.
|
||||
* @param {string} name The name of the bucket.
|
||||
* @param {object} [options] Configuration object.
|
||||
* @param {string} [options.userProject] User project.
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('albums');
|
||||
* ```
|
||||
*/
|
||||
declare class Bucket extends ServiceObject {
|
||||
metadata: Metadata;
|
||||
name: string;
|
||||
/**
|
||||
* A reference to the {@link Storage} associated with this {@link Bucket}
|
||||
* instance.
|
||||
* @name Bucket#storage
|
||||
* @type {Storage}
|
||||
*/
|
||||
storage: Storage;
|
||||
/**
|
||||
* A user project to apply to each request from this bucket.
|
||||
* @name Bucket#userProject
|
||||
* @type {string}
|
||||
*/
|
||||
userProject?: string;
|
||||
acl: Acl;
|
||||
iam: Iam;
|
||||
crc32cGenerator: CRC32CValidatorGenerator;
|
||||
getFilesStream(query?: GetFilesOptions): Readable;
|
||||
signer?: URLSigner;
|
||||
private instanceRetryValue?;
|
||||
instancePreconditionOpts?: PreconditionOptions;
|
||||
constructor(storage: Storage, name: string, options?: BucketOptions);
|
||||
/**
|
||||
* The bucket's Cloud Storage URI (`gs://`)
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
*
|
||||
* // `gs://my-bucket`
|
||||
* const href = bucket.cloudStorageURI.href;
|
||||
* ```
|
||||
*/
|
||||
get cloudStorageURI(): URL;
|
||||
addLifecycleRule(rule: LifecycleRule | LifecycleRule[], options?: AddLifecycleRuleOptions): Promise<SetBucketMetadataResponse>;
|
||||
addLifecycleRule(rule: LifecycleRule | LifecycleRule[], options: AddLifecycleRuleOptions, callback: SetBucketMetadataCallback): void;
|
||||
addLifecycleRule(rule: LifecycleRule | LifecycleRule[], callback: SetBucketMetadataCallback): void;
|
||||
combine(sources: string[] | File[], destination: string | File, options?: CombineOptions): Promise<CombineResponse>;
|
||||
combine(sources: string[] | File[], destination: string | File, options: CombineOptions, callback: CombineCallback): void;
|
||||
combine(sources: string[] | File[], destination: string | File, callback: CombineCallback): void;
|
||||
createChannel(id: string, config: CreateChannelConfig, options?: CreateChannelOptions): Promise<CreateChannelResponse>;
|
||||
createChannel(id: string, config: CreateChannelConfig, callback: CreateChannelCallback): void;
|
||||
createChannel(id: string, config: CreateChannelConfig, options: CreateChannelOptions, callback: CreateChannelCallback): void;
|
||||
createNotification(topic: string, options?: CreateNotificationOptions): Promise<CreateNotificationResponse>;
|
||||
createNotification(topic: string, options: CreateNotificationOptions, callback: CreateNotificationCallback): void;
|
||||
createNotification(topic: string, callback: CreateNotificationCallback): void;
|
||||
deleteFiles(query?: DeleteFilesOptions): Promise<void>;
|
||||
deleteFiles(callback: DeleteFilesCallback): void;
|
||||
deleteFiles(query: DeleteFilesOptions, callback: DeleteFilesCallback): void;
|
||||
deleteLabels(labels?: string | string[]): Promise<DeleteLabelsResponse>;
|
||||
deleteLabels(options: DeleteLabelsOptions): Promise<DeleteLabelsResponse>;
|
||||
deleteLabels(callback: DeleteLabelsCallback): void;
|
||||
deleteLabels(labels: string | string[], options: DeleteLabelsOptions): Promise<DeleteLabelsResponse>;
|
||||
deleteLabels(labels: string | string[], callback: DeleteLabelsCallback): void;
|
||||
deleteLabels(labels: string | string[], options: DeleteLabelsOptions, callback: DeleteLabelsCallback): void;
|
||||
disableRequesterPays(options?: DisableRequesterPaysOptions): Promise<DisableRequesterPaysResponse>;
|
||||
disableRequesterPays(callback: DisableRequesterPaysCallback): void;
|
||||
disableRequesterPays(options: DisableRequesterPaysOptions, callback: DisableRequesterPaysCallback): void;
|
||||
enableLogging(config: EnableLoggingOptions): Promise<SetBucketMetadataResponse>;
|
||||
enableLogging(config: EnableLoggingOptions, callback: SetBucketMetadataCallback): void;
|
||||
enableRequesterPays(options?: EnableRequesterPaysOptions): Promise<EnableRequesterPaysResponse>;
|
||||
enableRequesterPays(callback: EnableRequesterPaysCallback): void;
|
||||
enableRequesterPays(options: EnableRequesterPaysOptions, callback: EnableRequesterPaysCallback): void;
|
||||
/**
|
||||
* Create a {@link File} object. See {@link File} to see how to handle
|
||||
* the different use cases you may have.
|
||||
*
|
||||
* @param {string} name The name of the file in this bucket.
|
||||
* @param {FileOptions} [options] Configuration options.
|
||||
* @param {string|number} [options.generation] Only use a specific revision of
|
||||
* this file.
|
||||
* @param {string} [options.encryptionKey] A custom encryption key. See
|
||||
* {@link https://cloud.google.com/storage/docs/encryption#customer-supplied| Customer-supplied Encryption Keys}.
|
||||
* @param {string} [options.kmsKeyName] The name of the Cloud KMS key that will
|
||||
* be used to encrypt the object. Must be in the format:
|
||||
* `projects/my-project/locations/location/keyRings/my-kr/cryptoKeys/my-key`.
|
||||
* KMS key ring must use the same location as the bucket.
|
||||
* @param {string} [options.userProject] The ID of the project which will be
|
||||
* billed for all requests made from File object.
|
||||
* @returns {File}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('albums');
|
||||
* const file = bucket.file('my-existing-file.png');
|
||||
* ```
|
||||
*/
|
||||
file(name: string, options?: FileOptions): File;
|
||||
getFiles(query?: GetFilesOptions): Promise<GetFilesResponse>;
|
||||
getFiles(query: GetFilesOptions, callback: GetFilesCallback): void;
|
||||
getFiles(callback: GetFilesCallback): void;
|
||||
getLabels(options?: GetLabelsOptions): Promise<GetLabelsResponse>;
|
||||
getLabels(callback: GetLabelsCallback): void;
|
||||
getLabels(options: GetLabelsOptions, callback: GetLabelsCallback): void;
|
||||
getNotifications(options?: GetNotificationsOptions): Promise<GetNotificationsResponse>;
|
||||
getNotifications(callback: GetNotificationsCallback): void;
|
||||
getNotifications(options: GetNotificationsOptions, callback: GetNotificationsCallback): void;
|
||||
getSignedUrl(cfg: GetBucketSignedUrlConfig): Promise<GetSignedUrlResponse>;
|
||||
getSignedUrl(cfg: GetBucketSignedUrlConfig, callback: GetSignedUrlCallback): void;
|
||||
lock(metageneration: number | string): Promise<BucketLockResponse>;
|
||||
lock(metageneration: number | string, callback: BucketLockCallback): void;
|
||||
makePrivate(options?: MakeBucketPrivateOptions): Promise<MakeBucketPrivateResponse>;
|
||||
makePrivate(callback: MakeBucketPrivateCallback): void;
|
||||
makePrivate(options: MakeBucketPrivateOptions, callback: MakeBucketPrivateCallback): void;
|
||||
makePublic(options?: MakeBucketPublicOptions): Promise<MakeBucketPublicResponse>;
|
||||
makePublic(callback: MakeBucketPublicCallback): void;
|
||||
makePublic(options: MakeBucketPublicOptions, callback: MakeBucketPublicCallback): void;
|
||||
/**
|
||||
* Get a reference to a Cloud Pub/Sub Notification.
|
||||
*
|
||||
* @param {string} id ID of notification.
|
||||
* @returns {Notification}
|
||||
* @see Notification
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
* const notification = bucket.notification('1');
|
||||
* ```
|
||||
*/
|
||||
notification(id: string): Notification;
|
||||
removeRetentionPeriod(options?: SetBucketMetadataOptions): Promise<SetBucketMetadataResponse>;
|
||||
removeRetentionPeriod(callback: SetBucketMetadataCallback): void;
|
||||
removeRetentionPeriod(options: SetBucketMetadataOptions, callback: SetBucketMetadataCallback): void;
|
||||
request(reqOpts: DecorateRequestOptions): Promise<[ResponseBody, Metadata]>;
|
||||
request(reqOpts: DecorateRequestOptions, callback: BodyResponseCallback): void;
|
||||
setLabels(labels: Labels, options?: SetLabelsOptions): Promise<SetLabelsResponse>;
|
||||
setLabels(labels: Labels, callback: SetLabelsCallback): void;
|
||||
setLabels(labels: Labels, options: SetLabelsOptions, callback: SetLabelsCallback): void;
|
||||
setMetadata(metadata: Metadata, options?: SetMetadataOptions): Promise<SetMetadataResponse>;
|
||||
setMetadata(metadata: Metadata, callback: MetadataCallback): void;
|
||||
setMetadata(metadata: Metadata, options: SetMetadataOptions, callback: MetadataCallback): void;
|
||||
setRetentionPeriod(duration: number, options?: SetBucketMetadataOptions): Promise<SetBucketMetadataResponse>;
|
||||
setRetentionPeriod(duration: number, callback: SetBucketMetadataCallback): void;
|
||||
setRetentionPeriod(duration: number, options: SetBucketMetadataOptions, callback: SetBucketMetadataCallback): void;
|
||||
setCorsConfiguration(corsConfiguration: Cors[], options?: SetBucketMetadataOptions): Promise<SetBucketMetadataResponse>;
|
||||
setCorsConfiguration(corsConfiguration: Cors[], callback: SetBucketMetadataCallback): void;
|
||||
setCorsConfiguration(corsConfiguration: Cors[], options: SetBucketMetadataOptions, callback: SetBucketMetadataCallback): void;
|
||||
setStorageClass(storageClass: string, options?: SetBucketStorageClassOptions): Promise<SetBucketMetadataResponse>;
|
||||
setStorageClass(storageClass: string, callback: SetBucketStorageClassCallback): void;
|
||||
setStorageClass(storageClass: string, options: SetBucketStorageClassOptions, callback: SetBucketStorageClassCallback): void;
|
||||
/**
|
||||
* Set a user project to be billed for all requests made from this Bucket
|
||||
* object and any files referenced from this Bucket object.
|
||||
*
|
||||
* @param {string} userProject The user project.
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('albums');
|
||||
*
|
||||
* bucket.setUserProject('grape-spaceship-123');
|
||||
* ```
|
||||
*/
|
||||
setUserProject(userProject: string): void;
|
||||
upload(pathString: string, options?: UploadOptions): Promise<UploadResponse>;
|
||||
upload(pathString: string, options: UploadOptions, callback: UploadCallback): void;
|
||||
upload(pathString: string, callback: UploadCallback): void;
|
||||
makeAllFilesPublicPrivate_(options?: MakeAllFilesPublicPrivateOptions): Promise<MakeAllFilesPublicPrivateResponse>;
|
||||
makeAllFilesPublicPrivate_(callback: MakeAllFilesPublicPrivateCallback): void;
|
||||
makeAllFilesPublicPrivate_(options: MakeAllFilesPublicPrivateOptions, callback: MakeAllFilesPublicPrivateCallback): void;
|
||||
getId(): string;
|
||||
disableAutoRetryConditionallyIdempotent_(coreOpts: any, methodType: AvailableServiceObjectMethods, localPreconditionOptions?: PreconditionOptions): void;
|
||||
}
|
||||
/**
|
||||
* Reference to the {@link Bucket} class.
|
||||
* @name module:@google-cloud/storage.Bucket
|
||||
* @see Bucket
|
||||
*/
|
||||
export { Bucket };
|
||||
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,33 @@
|
||||
import { Metadata, ServiceObject } from './nodejs-common';
|
||||
import { Storage } from './storage';
|
||||
export interface StopCallback {
|
||||
(err: Error | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
/**
|
||||
* Create a channel object to interact with a Cloud Storage channel.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/object-change-notification| Object Change Notification}
|
||||
*
|
||||
* @class
|
||||
*
|
||||
* @param {string} id The ID of the channel.
|
||||
* @param {string} resourceId The resource ID of the channel.
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const channel = storage.channel('id', 'resource-id');
|
||||
* ```
|
||||
*/
|
||||
declare class Channel extends ServiceObject {
|
||||
constructor(storage: Storage, id: string, resourceId: string);
|
||||
stop(): Promise<Metadata>;
|
||||
stop(callback: StopCallback): void;
|
||||
}
|
||||
/**
|
||||
* Reference to the {@link Channel} class.
|
||||
* @name module:@google-cloud/storage.Channel
|
||||
* @see Channel
|
||||
*/
|
||||
export { Channel };
|
||||
@ -0,0 +1,105 @@
|
||||
"use strict";
|
||||
// Copyright 2019 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.Channel = void 0;
|
||||
const nodejs_common_1 = require("./nodejs-common");
|
||||
const promisify_1 = require("@google-cloud/promisify");
|
||||
/**
|
||||
* Create a channel object to interact with a Cloud Storage channel.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/object-change-notification| Object Change Notification}
|
||||
*
|
||||
* @class
|
||||
*
|
||||
* @param {string} id The ID of the channel.
|
||||
* @param {string} resourceId The resource ID of the channel.
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const channel = storage.channel('id', 'resource-id');
|
||||
* ```
|
||||
*/
|
||||
class Channel extends nodejs_common_1.ServiceObject {
|
||||
constructor(storage, id, resourceId) {
|
||||
const config = {
|
||||
parent: storage,
|
||||
baseUrl: '/channels',
|
||||
// An ID shouldn't be included in the API requests.
|
||||
// RE:
|
||||
// https://github.com/GoogleCloudPlatform/google-cloud-node/issues/1145
|
||||
id: '',
|
||||
methods: {
|
||||
// Only need `request`.
|
||||
},
|
||||
};
|
||||
super(config);
|
||||
this.metadata.id = id;
|
||||
this.metadata.resourceId = resourceId;
|
||||
}
|
||||
/**
|
||||
* @typedef {array} StopResponse
|
||||
* @property {object} 0 The full API response.
|
||||
*/
|
||||
/**
|
||||
* @callback StopCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
/**
|
||||
* Stop this channel.
|
||||
*
|
||||
* @param {StopCallback} [callback] Callback function.
|
||||
* @returns {Promise<StopResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const channel = storage.channel('id', 'resource-id');
|
||||
* channel.stop(function(err, apiResponse) {
|
||||
* if (!err) {
|
||||
* // Channel stopped successfully.
|
||||
* }
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* channel.stop().then(function(data) {
|
||||
* const apiResponse = data[0];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
stop(callback) {
|
||||
callback = callback || nodejs_common_1.util.noop;
|
||||
this.request({
|
||||
method: 'POST',
|
||||
uri: '/stop',
|
||||
json: this.metadata,
|
||||
}, (err, apiResponse) => {
|
||||
callback(err, apiResponse);
|
||||
});
|
||||
}
|
||||
}
|
||||
exports.Channel = Channel;
|
||||
/*! Developer Documentation
|
||||
*
|
||||
* All async methods (except for streams) will return a Promise in the event
|
||||
* that a callback is omitted.
|
||||
*/
|
||||
(0, promisify_1.promisifyAll)(Channel);
|
||||
//# sourceMappingURL=channel.js.map
|
||||
@ -0,0 +1,145 @@
|
||||
/// <reference types="node" />
|
||||
/// <reference types="node" />
|
||||
import { PathLike } from 'fs';
|
||||
/**
|
||||
* Ported from {@link https://github.com/google/crc32c/blob/21fc8ef30415a635e7351ffa0e5d5367943d4a94/src/crc32c_portable.cc#L16-L59 github.com/google/crc32c}
|
||||
*/
|
||||
declare const CRC32C_EXTENSIONS: readonly [0, 4067132163, 3778769143, 324072436, 3348797215, 904991772, 648144872, 3570033899, 2329499855, 2024987596, 1809983544, 2575936315, 1296289744, 3207089363, 2893594407, 1578318884, 274646895, 3795141740, 4049975192, 51262619, 3619967088, 632279923, 922689671, 3298075524, 2592579488, 1760304291, 2075979607, 2312596564, 1562183871, 2943781820, 3156637768, 1313733451, 549293790, 3537243613, 3246849577, 871202090, 3878099393, 357341890, 102525238, 4101499445, 2858735121, 1477399826, 1264559846, 3107202533, 1845379342, 2677391885, 2361733625, 2125378298, 820201905, 3263744690, 3520608582, 598981189, 4151959214, 85089709, 373468761, 3827903834, 3124367742, 1213305469, 1526817161, 2842354314, 2107672161, 2412447074, 2627466902, 1861252501, 1098587580, 3004210879, 2688576843, 1378610760, 2262928035, 1955203488, 1742404180, 2511436119, 3416409459, 969524848, 714683780, 3639785095, 205050476, 4266873199, 3976438427, 526918040, 1361435347, 2739821008, 2954799652, 1114974503, 2529119692, 1691668175, 2005155131, 2247081528, 3690758684, 697762079, 986182379, 3366744552, 476452099, 3993867776, 4250756596, 255256311, 1640403810, 2477592673, 2164122517, 1922457750, 2791048317, 1412925310, 1197962378, 3037525897, 3944729517, 427051182, 170179418, 4165941337, 746937522, 3740196785, 3451792453, 1070968646, 1905808397, 2213795598, 2426610938, 1657317369, 3053634322, 1147748369, 1463399397, 2773627110, 4215344322, 153784257, 444234805, 3893493558, 1021025245, 3467647198, 3722505002, 797665321, 2197175160, 1889384571, 1674398607, 2443626636, 1164749927, 3070701412, 2757221520, 1446797203, 137323447, 4198817972, 3910406976, 461344835, 3484808360, 1037989803, 781091935, 3705997148, 2460548119, 1623424788, 1939049696, 2180517859, 1429367560, 2807687179, 3020495871, 1180866812, 410100952, 3927582683, 4182430767, 186734380, 3756733383, 763408580, 1053836080, 3434856499, 2722870694, 1344288421, 1131464017, 2971354706, 1708204729, 2545590714, 2229949006, 1988219213, 680717673, 3673779818, 3383336350, 1002577565, 4010310262, 493091189, 238226049, 4233660802, 2987750089, 1082061258, 1395524158, 2705686845, 1972364758, 2279892693, 2494862625, 1725896226, 952904198, 3399985413, 3656866545, 731699698, 4283874585, 222117402, 510512622, 3959836397, 3280807620, 837199303, 582374963, 3504198960, 68661723, 4135334616, 3844915500, 390545967, 1230274059, 3141532936, 2825850620, 1510247935, 2395924756, 2091215383, 1878366691, 2644384480, 3553878443, 565732008, 854102364, 3229815391, 340358836, 3861050807, 4117890627, 119113024, 1493875044, 2875275879, 3090270611, 1247431312, 2660249211, 1828433272, 2141937292, 2378227087, 3811616794, 291187481, 34330861, 4032846830, 615137029, 3603020806, 3314634738, 939183345, 1776939221, 2609017814, 2295496738, 2058945313, 2926798794, 1545135305, 1330124605, 3173225534, 4084100981, 17165430, 307568514, 3762199681, 888469610, 3332340585, 3587147933, 665062302, 2042050490, 2346497209, 2559330125, 1793573966, 3190661285, 1279665062, 1595330642, 2910671697];
|
||||
declare const CRC32C_EXTENSION_TABLE: Int32Array;
|
||||
/** An interface for CRC32C hashing and validation */
|
||||
interface CRC32CValidator {
|
||||
/**
|
||||
* A method returning the CRC32C as a base64-encoded string.
|
||||
*
|
||||
* @example
|
||||
* Hashing the string 'data' should return 'rth90Q=='
|
||||
*
|
||||
* ```js
|
||||
* const buffer = Buffer.from('data');
|
||||
* crc32c.update(buffer);
|
||||
* crc32c.toString(); // 'rth90Q=='
|
||||
* ```
|
||||
**/
|
||||
toString: () => string;
|
||||
/**
|
||||
* A method validating a base64-encoded CRC32C string.
|
||||
*
|
||||
* @example
|
||||
* Should return `true` if the value matches, `false` otherwise
|
||||
*
|
||||
* ```js
|
||||
* const buffer = Buffer.from('data');
|
||||
* crc32c.update(buffer);
|
||||
* crc32c.validate('DkjKuA=='); // false
|
||||
* crc32c.validate('rth90Q=='); // true
|
||||
* ```
|
||||
*/
|
||||
validate: (value: string) => boolean;
|
||||
/**
|
||||
* A method for passing `Buffer`s for CRC32C generation.
|
||||
*
|
||||
* @example
|
||||
* Hashing buffers from 'some ' and 'text\n'
|
||||
*
|
||||
* ```js
|
||||
* const buffer1 = Buffer.from('some ');
|
||||
* crc32c.update(buffer1);
|
||||
*
|
||||
* const buffer2 = Buffer.from('text\n');
|
||||
* crc32c.update(buffer2);
|
||||
*
|
||||
* crc32c.toString(); // 'DkjKuA=='
|
||||
* ```
|
||||
*/
|
||||
update: (data: Buffer) => void;
|
||||
}
|
||||
/** A function that generates a CRC32C Validator */
|
||||
interface CRC32CValidatorGenerator {
|
||||
/** Should return a new, ready-to-use `CRC32CValidator` */
|
||||
(): CRC32CValidator;
|
||||
}
|
||||
declare const CRC32C_DEFAULT_VALIDATOR_GENERATOR: CRC32CValidatorGenerator;
|
||||
declare const CRC32C_EXCEPTION_MESSAGES: {
|
||||
readonly INVALID_INIT_BASE64_RANGE: (l: number) => string;
|
||||
readonly INVALID_INIT_BUFFER_LENGTH: (l: number) => string;
|
||||
readonly INVALID_INIT_INTEGER: (l: number) => string;
|
||||
};
|
||||
declare class CRC32C implements CRC32CValidator {
|
||||
#private;
|
||||
/**
|
||||
* Constructs a new `CRC32C` object.
|
||||
*
|
||||
* Reconstruction is recommended via the `CRC32C.from` static method.
|
||||
*
|
||||
* @param initialValue An initial CRC32C value - a signed 32-bit integer.
|
||||
*/
|
||||
constructor(initialValue?: number);
|
||||
/**
|
||||
* Calculates a CRC32C from a provided buffer.
|
||||
*
|
||||
* Implementation inspired from:
|
||||
* - {@link https://github.com/google/crc32c/blob/21fc8ef30415a635e7351ffa0e5d5367943d4a94/src/crc32c_portable.cc github.com/google/crc32c}
|
||||
* - {@link https://github.com/googleapis/python-crc32c/blob/a595e758c08df445a99c3bf132ee8e80a3ec4308/src/google_crc32c/python.py github.com/googleapis/python-crc32c}
|
||||
* - {@link https://github.com/googleapis/java-storage/pull/1376/files github.com/googleapis/java-storage}
|
||||
*
|
||||
* @param data The `Buffer` to generate the CRC32C from
|
||||
*/
|
||||
update(data: Buffer): void;
|
||||
/**
|
||||
* Validates a provided input to the current CRC32C value.
|
||||
*
|
||||
* @param input A Buffer, `CRC32C`-compatible object, base64-encoded data (string), or signed 32-bit integer
|
||||
*/
|
||||
validate(input: Buffer | CRC32CValidator | string | number): boolean;
|
||||
/**
|
||||
* Returns a `Buffer` representation of the CRC32C value
|
||||
*/
|
||||
toBuffer(): Buffer;
|
||||
/**
|
||||
* Returns a JSON-compatible, base64-encoded representation of the CRC32C value.
|
||||
*
|
||||
* See {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/JSON/stringify `JSON#stringify`}
|
||||
*/
|
||||
toJSON(): string;
|
||||
/**
|
||||
* Returns a base64-encoded representation of the CRC32C value.
|
||||
*
|
||||
* See {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/toString `Object#toString`}
|
||||
*/
|
||||
toString(): string;
|
||||
/**
|
||||
* Returns the `number` representation of the CRC32C value as a signed 32-bit integer
|
||||
*
|
||||
* See {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/valueOf `Object#valueOf`}
|
||||
*/
|
||||
valueOf(): number;
|
||||
static readonly CRC32C_EXTENSIONS: readonly [0, 4067132163, 3778769143, 324072436, 3348797215, 904991772, 648144872, 3570033899, 2329499855, 2024987596, 1809983544, 2575936315, 1296289744, 3207089363, 2893594407, 1578318884, 274646895, 3795141740, 4049975192, 51262619, 3619967088, 632279923, 922689671, 3298075524, 2592579488, 1760304291, 2075979607, 2312596564, 1562183871, 2943781820, 3156637768, 1313733451, 549293790, 3537243613, 3246849577, 871202090, 3878099393, 357341890, 102525238, 4101499445, 2858735121, 1477399826, 1264559846, 3107202533, 1845379342, 2677391885, 2361733625, 2125378298, 820201905, 3263744690, 3520608582, 598981189, 4151959214, 85089709, 373468761, 3827903834, 3124367742, 1213305469, 1526817161, 2842354314, 2107672161, 2412447074, 2627466902, 1861252501, 1098587580, 3004210879, 2688576843, 1378610760, 2262928035, 1955203488, 1742404180, 2511436119, 3416409459, 969524848, 714683780, 3639785095, 205050476, 4266873199, 3976438427, 526918040, 1361435347, 2739821008, 2954799652, 1114974503, 2529119692, 1691668175, 2005155131, 2247081528, 3690758684, 697762079, 986182379, 3366744552, 476452099, 3993867776, 4250756596, 255256311, 1640403810, 2477592673, 2164122517, 1922457750, 2791048317, 1412925310, 1197962378, 3037525897, 3944729517, 427051182, 170179418, 4165941337, 746937522, 3740196785, 3451792453, 1070968646, 1905808397, 2213795598, 2426610938, 1657317369, 3053634322, 1147748369, 1463399397, 2773627110, 4215344322, 153784257, 444234805, 3893493558, 1021025245, 3467647198, 3722505002, 797665321, 2197175160, 1889384571, 1674398607, 2443626636, 1164749927, 3070701412, 2757221520, 1446797203, 137323447, 4198817972, 3910406976, 461344835, 3484808360, 1037989803, 781091935, 3705997148, 2460548119, 1623424788, 1939049696, 2180517859, 1429367560, 2807687179, 3020495871, 1180866812, 410100952, 3927582683, 4182430767, 186734380, 3756733383, 763408580, 1053836080, 3434856499, 2722870694, 1344288421, 1131464017, 2971354706, 1708204729, 2545590714, 2229949006, 1988219213, 680717673, 3673779818, 3383336350, 1002577565, 4010310262, 493091189, 238226049, 4233660802, 2987750089, 1082061258, 1395524158, 2705686845, 1972364758, 2279892693, 2494862625, 1725896226, 952904198, 3399985413, 3656866545, 731699698, 4283874585, 222117402, 510512622, 3959836397, 3280807620, 837199303, 582374963, 3504198960, 68661723, 4135334616, 3844915500, 390545967, 1230274059, 3141532936, 2825850620, 1510247935, 2395924756, 2091215383, 1878366691, 2644384480, 3553878443, 565732008, 854102364, 3229815391, 340358836, 3861050807, 4117890627, 119113024, 1493875044, 2875275879, 3090270611, 1247431312, 2660249211, 1828433272, 2141937292, 2378227087, 3811616794, 291187481, 34330861, 4032846830, 615137029, 3603020806, 3314634738, 939183345, 1776939221, 2609017814, 2295496738, 2058945313, 2926798794, 1545135305, 1330124605, 3173225534, 4084100981, 17165430, 307568514, 3762199681, 888469610, 3332340585, 3587147933, 665062302, 2042050490, 2346497209, 2559330125, 1793573966, 3190661285, 1279665062, 1595330642, 2910671697];
|
||||
static readonly CRC32C_EXTENSION_TABLE: Int32Array;
|
||||
/**
|
||||
* Generates a `CRC32C` from a compatible buffer format.
|
||||
*
|
||||
* @param value 4-byte `ArrayBufferView`/`Buffer`/`TypedArray`
|
||||
*/
|
||||
private static fromBuffer;
|
||||
static fromFile(file: PathLike): Promise<CRC32C>;
|
||||
/**
|
||||
* Generates a `CRC32C` from 4-byte base64-encoded data (string).
|
||||
*
|
||||
* @param value 4-byte base64-encoded data (string)
|
||||
*/
|
||||
private static fromString;
|
||||
/**
|
||||
* Generates a `CRC32C` from a safe, unsigned 32-bit integer.
|
||||
*
|
||||
* @param value an unsigned 32-bit integer
|
||||
*/
|
||||
private static fromNumber;
|
||||
/**
|
||||
* Generates a `CRC32C` from a variety of compatable types.
|
||||
* Note: strings are treated as input, not as file paths to read from.
|
||||
*
|
||||
* @param value A number, 4-byte `ArrayBufferView`/`Buffer`/`TypedArray`, or 4-byte base64-encoded data (string)
|
||||
*/
|
||||
static from(value: ArrayBuffer | ArrayBufferView | CRC32CValidator | string | number): CRC32C;
|
||||
}
|
||||
export { CRC32C, CRC32C_DEFAULT_VALIDATOR_GENERATOR, CRC32C_EXCEPTION_MESSAGES, CRC32C_EXTENSIONS, CRC32C_EXTENSION_TABLE, CRC32CValidator, CRC32CValidatorGenerator, };
|
||||
@ -0,0 +1,255 @@
|
||||
"use strict";
|
||||
// Copyright 2022 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {
|
||||
if (kind === "m") throw new TypeError("Private method is not writable");
|
||||
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter");
|
||||
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it");
|
||||
return (kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;
|
||||
};
|
||||
var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
|
||||
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
|
||||
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
||||
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
||||
};
|
||||
var _CRC32C_crc32c;
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.CRC32C_EXTENSION_TABLE = exports.CRC32C_EXTENSIONS = exports.CRC32C_EXCEPTION_MESSAGES = exports.CRC32C_DEFAULT_VALIDATOR_GENERATOR = exports.CRC32C = void 0;
|
||||
const fs_1 = require("fs");
|
||||
/**
|
||||
* Ported from {@link https://github.com/google/crc32c/blob/21fc8ef30415a635e7351ffa0e5d5367943d4a94/src/crc32c_portable.cc#L16-L59 github.com/google/crc32c}
|
||||
*/
|
||||
const CRC32C_EXTENSIONS = [
|
||||
0x00000000, 0xf26b8303, 0xe13b70f7, 0x1350f3f4, 0xc79a971f, 0x35f1141c,
|
||||
0x26a1e7e8, 0xd4ca64eb, 0x8ad958cf, 0x78b2dbcc, 0x6be22838, 0x9989ab3b,
|
||||
0x4d43cfd0, 0xbf284cd3, 0xac78bf27, 0x5e133c24, 0x105ec76f, 0xe235446c,
|
||||
0xf165b798, 0x030e349b, 0xd7c45070, 0x25afd373, 0x36ff2087, 0xc494a384,
|
||||
0x9a879fa0, 0x68ec1ca3, 0x7bbcef57, 0x89d76c54, 0x5d1d08bf, 0xaf768bbc,
|
||||
0xbc267848, 0x4e4dfb4b, 0x20bd8ede, 0xd2d60ddd, 0xc186fe29, 0x33ed7d2a,
|
||||
0xe72719c1, 0x154c9ac2, 0x061c6936, 0xf477ea35, 0xaa64d611, 0x580f5512,
|
||||
0x4b5fa6e6, 0xb93425e5, 0x6dfe410e, 0x9f95c20d, 0x8cc531f9, 0x7eaeb2fa,
|
||||
0x30e349b1, 0xc288cab2, 0xd1d83946, 0x23b3ba45, 0xf779deae, 0x05125dad,
|
||||
0x1642ae59, 0xe4292d5a, 0xba3a117e, 0x4851927d, 0x5b016189, 0xa96ae28a,
|
||||
0x7da08661, 0x8fcb0562, 0x9c9bf696, 0x6ef07595, 0x417b1dbc, 0xb3109ebf,
|
||||
0xa0406d4b, 0x522bee48, 0x86e18aa3, 0x748a09a0, 0x67dafa54, 0x95b17957,
|
||||
0xcba24573, 0x39c9c670, 0x2a993584, 0xd8f2b687, 0x0c38d26c, 0xfe53516f,
|
||||
0xed03a29b, 0x1f682198, 0x5125dad3, 0xa34e59d0, 0xb01eaa24, 0x42752927,
|
||||
0x96bf4dcc, 0x64d4cecf, 0x77843d3b, 0x85efbe38, 0xdbfc821c, 0x2997011f,
|
||||
0x3ac7f2eb, 0xc8ac71e8, 0x1c661503, 0xee0d9600, 0xfd5d65f4, 0x0f36e6f7,
|
||||
0x61c69362, 0x93ad1061, 0x80fde395, 0x72966096, 0xa65c047d, 0x5437877e,
|
||||
0x4767748a, 0xb50cf789, 0xeb1fcbad, 0x197448ae, 0x0a24bb5a, 0xf84f3859,
|
||||
0x2c855cb2, 0xdeeedfb1, 0xcdbe2c45, 0x3fd5af46, 0x7198540d, 0x83f3d70e,
|
||||
0x90a324fa, 0x62c8a7f9, 0xb602c312, 0x44694011, 0x5739b3e5, 0xa55230e6,
|
||||
0xfb410cc2, 0x092a8fc1, 0x1a7a7c35, 0xe811ff36, 0x3cdb9bdd, 0xceb018de,
|
||||
0xdde0eb2a, 0x2f8b6829, 0x82f63b78, 0x709db87b, 0x63cd4b8f, 0x91a6c88c,
|
||||
0x456cac67, 0xb7072f64, 0xa457dc90, 0x563c5f93, 0x082f63b7, 0xfa44e0b4,
|
||||
0xe9141340, 0x1b7f9043, 0xcfb5f4a8, 0x3dde77ab, 0x2e8e845f, 0xdce5075c,
|
||||
0x92a8fc17, 0x60c37f14, 0x73938ce0, 0x81f80fe3, 0x55326b08, 0xa759e80b,
|
||||
0xb4091bff, 0x466298fc, 0x1871a4d8, 0xea1a27db, 0xf94ad42f, 0x0b21572c,
|
||||
0xdfeb33c7, 0x2d80b0c4, 0x3ed04330, 0xccbbc033, 0xa24bb5a6, 0x502036a5,
|
||||
0x4370c551, 0xb11b4652, 0x65d122b9, 0x97baa1ba, 0x84ea524e, 0x7681d14d,
|
||||
0x2892ed69, 0xdaf96e6a, 0xc9a99d9e, 0x3bc21e9d, 0xef087a76, 0x1d63f975,
|
||||
0x0e330a81, 0xfc588982, 0xb21572c9, 0x407ef1ca, 0x532e023e, 0xa145813d,
|
||||
0x758fe5d6, 0x87e466d5, 0x94b49521, 0x66df1622, 0x38cc2a06, 0xcaa7a905,
|
||||
0xd9f75af1, 0x2b9cd9f2, 0xff56bd19, 0x0d3d3e1a, 0x1e6dcdee, 0xec064eed,
|
||||
0xc38d26c4, 0x31e6a5c7, 0x22b65633, 0xd0ddd530, 0x0417b1db, 0xf67c32d8,
|
||||
0xe52cc12c, 0x1747422f, 0x49547e0b, 0xbb3ffd08, 0xa86f0efc, 0x5a048dff,
|
||||
0x8ecee914, 0x7ca56a17, 0x6ff599e3, 0x9d9e1ae0, 0xd3d3e1ab, 0x21b862a8,
|
||||
0x32e8915c, 0xc083125f, 0x144976b4, 0xe622f5b7, 0xf5720643, 0x07198540,
|
||||
0x590ab964, 0xab613a67, 0xb831c993, 0x4a5a4a90, 0x9e902e7b, 0x6cfbad78,
|
||||
0x7fab5e8c, 0x8dc0dd8f, 0xe330a81a, 0x115b2b19, 0x020bd8ed, 0xf0605bee,
|
||||
0x24aa3f05, 0xd6c1bc06, 0xc5914ff2, 0x37faccf1, 0x69e9f0d5, 0x9b8273d6,
|
||||
0x88d28022, 0x7ab90321, 0xae7367ca, 0x5c18e4c9, 0x4f48173d, 0xbd23943e,
|
||||
0xf36e6f75, 0x0105ec76, 0x12551f82, 0xe03e9c81, 0x34f4f86a, 0xc69f7b69,
|
||||
0xd5cf889d, 0x27a40b9e, 0x79b737ba, 0x8bdcb4b9, 0x988c474d, 0x6ae7c44e,
|
||||
0xbe2da0a5, 0x4c4623a6, 0x5f16d052, 0xad7d5351,
|
||||
];
|
||||
exports.CRC32C_EXTENSIONS = CRC32C_EXTENSIONS;
|
||||
const CRC32C_EXTENSION_TABLE = new Int32Array(CRC32C_EXTENSIONS);
|
||||
exports.CRC32C_EXTENSION_TABLE = CRC32C_EXTENSION_TABLE;
|
||||
const CRC32C_DEFAULT_VALIDATOR_GENERATOR = () => new CRC32C();
|
||||
exports.CRC32C_DEFAULT_VALIDATOR_GENERATOR = CRC32C_DEFAULT_VALIDATOR_GENERATOR;
|
||||
const CRC32C_EXCEPTION_MESSAGES = {
|
||||
INVALID_INIT_BASE64_RANGE: (l) => `base64-encoded data expected to equal 4 bytes, not ${l}`,
|
||||
INVALID_INIT_BUFFER_LENGTH: (l) => `Buffer expected to equal 4 bytes, not ${l}`,
|
||||
INVALID_INIT_INTEGER: (l) => `Number expected to be a safe, unsigned 32-bit integer, not ${l}`,
|
||||
};
|
||||
exports.CRC32C_EXCEPTION_MESSAGES = CRC32C_EXCEPTION_MESSAGES;
|
||||
class CRC32C {
|
||||
/**
|
||||
* Constructs a new `CRC32C` object.
|
||||
*
|
||||
* Reconstruction is recommended via the `CRC32C.from` static method.
|
||||
*
|
||||
* @param initialValue An initial CRC32C value - a signed 32-bit integer.
|
||||
*/
|
||||
constructor(initialValue = 0) {
|
||||
/** Current CRC32C value */
|
||||
_CRC32C_crc32c.set(this, 0);
|
||||
__classPrivateFieldSet(this, _CRC32C_crc32c, initialValue, "f");
|
||||
}
|
||||
/**
|
||||
* Calculates a CRC32C from a provided buffer.
|
||||
*
|
||||
* Implementation inspired from:
|
||||
* - {@link https://github.com/google/crc32c/blob/21fc8ef30415a635e7351ffa0e5d5367943d4a94/src/crc32c_portable.cc github.com/google/crc32c}
|
||||
* - {@link https://github.com/googleapis/python-crc32c/blob/a595e758c08df445a99c3bf132ee8e80a3ec4308/src/google_crc32c/python.py github.com/googleapis/python-crc32c}
|
||||
* - {@link https://github.com/googleapis/java-storage/pull/1376/files github.com/googleapis/java-storage}
|
||||
*
|
||||
* @param data The `Buffer` to generate the CRC32C from
|
||||
*/
|
||||
update(data) {
|
||||
let current = __classPrivateFieldGet(this, _CRC32C_crc32c, "f") ^ 0xffffffff;
|
||||
for (const d of data) {
|
||||
const tablePoly = CRC32C.CRC32C_EXTENSION_TABLE[(d ^ current) & 0xff];
|
||||
current = tablePoly ^ (current >>> 8);
|
||||
}
|
||||
__classPrivateFieldSet(this, _CRC32C_crc32c, current ^ 0xffffffff, "f");
|
||||
}
|
||||
/**
|
||||
* Validates a provided input to the current CRC32C value.
|
||||
*
|
||||
* @param input A Buffer, `CRC32C`-compatible object, base64-encoded data (string), or signed 32-bit integer
|
||||
*/
|
||||
validate(input) {
|
||||
if (typeof input === 'number') {
|
||||
return input === __classPrivateFieldGet(this, _CRC32C_crc32c, "f");
|
||||
}
|
||||
else if (typeof input === 'string') {
|
||||
return input === this.toString();
|
||||
}
|
||||
else if (Buffer.isBuffer(input)) {
|
||||
return Buffer.compare(input, this.toBuffer()) === 0;
|
||||
}
|
||||
else {
|
||||
// `CRC32C`-like object
|
||||
return input.toString() === this.toString();
|
||||
}
|
||||
}
|
||||
/**
|
||||
* Returns a `Buffer` representation of the CRC32C value
|
||||
*/
|
||||
toBuffer() {
|
||||
const buffer = Buffer.alloc(4);
|
||||
buffer.writeInt32BE(__classPrivateFieldGet(this, _CRC32C_crc32c, "f"));
|
||||
return buffer;
|
||||
}
|
||||
/**
|
||||
* Returns a JSON-compatible, base64-encoded representation of the CRC32C value.
|
||||
*
|
||||
* See {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/JSON/stringify `JSON#stringify`}
|
||||
*/
|
||||
toJSON() {
|
||||
return this.toString();
|
||||
}
|
||||
/**
|
||||
* Returns a base64-encoded representation of the CRC32C value.
|
||||
*
|
||||
* See {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/toString `Object#toString`}
|
||||
*/
|
||||
toString() {
|
||||
return this.toBuffer().toString('base64');
|
||||
}
|
||||
/**
|
||||
* Returns the `number` representation of the CRC32C value as a signed 32-bit integer
|
||||
*
|
||||
* See {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/valueOf `Object#valueOf`}
|
||||
*/
|
||||
valueOf() {
|
||||
return __classPrivateFieldGet(this, _CRC32C_crc32c, "f");
|
||||
}
|
||||
/**
|
||||
* Generates a `CRC32C` from a compatible buffer format.
|
||||
*
|
||||
* @param value 4-byte `ArrayBufferView`/`Buffer`/`TypedArray`
|
||||
*/
|
||||
static fromBuffer(value) {
|
||||
let buffer;
|
||||
if (Buffer.isBuffer(value)) {
|
||||
buffer = value;
|
||||
}
|
||||
else if ('buffer' in value) {
|
||||
// `ArrayBufferView`
|
||||
buffer = Buffer.from(value.buffer);
|
||||
}
|
||||
else {
|
||||
// `ArrayBuffer`
|
||||
buffer = Buffer.from(value);
|
||||
}
|
||||
if (buffer.byteLength !== 4) {
|
||||
throw new RangeError(CRC32C_EXCEPTION_MESSAGES.INVALID_INIT_BUFFER_LENGTH(buffer.byteLength));
|
||||
}
|
||||
return new CRC32C(buffer.readInt32BE());
|
||||
}
|
||||
static async fromFile(file) {
|
||||
const crc32c = new CRC32C();
|
||||
await new Promise((resolve, reject) => {
|
||||
(0, fs_1.createReadStream)(file)
|
||||
.on('data', (d) => crc32c.update(d))
|
||||
.on('end', resolve)
|
||||
.on('error', reject);
|
||||
});
|
||||
return crc32c;
|
||||
}
|
||||
/**
|
||||
* Generates a `CRC32C` from 4-byte base64-encoded data (string).
|
||||
*
|
||||
* @param value 4-byte base64-encoded data (string)
|
||||
*/
|
||||
static fromString(value) {
|
||||
const buffer = Buffer.from(value, 'base64');
|
||||
if (buffer.byteLength !== 4) {
|
||||
throw new RangeError(CRC32C_EXCEPTION_MESSAGES.INVALID_INIT_BASE64_RANGE(buffer.byteLength));
|
||||
}
|
||||
return this.fromBuffer(buffer);
|
||||
}
|
||||
/**
|
||||
* Generates a `CRC32C` from a safe, unsigned 32-bit integer.
|
||||
*
|
||||
* @param value an unsigned 32-bit integer
|
||||
*/
|
||||
static fromNumber(value) {
|
||||
if (!Number.isSafeInteger(value) || value > 2 ** 32 || value < -(2 ** 32)) {
|
||||
throw new RangeError(CRC32C_EXCEPTION_MESSAGES.INVALID_INIT_INTEGER(value));
|
||||
}
|
||||
return new CRC32C(value);
|
||||
}
|
||||
/**
|
||||
* Generates a `CRC32C` from a variety of compatable types.
|
||||
* Note: strings are treated as input, not as file paths to read from.
|
||||
*
|
||||
* @param value A number, 4-byte `ArrayBufferView`/`Buffer`/`TypedArray`, or 4-byte base64-encoded data (string)
|
||||
*/
|
||||
static from(value) {
|
||||
if (typeof value === 'number') {
|
||||
return this.fromNumber(value);
|
||||
}
|
||||
else if (typeof value === 'string') {
|
||||
return this.fromString(value);
|
||||
}
|
||||
else if ('byteLength' in value) {
|
||||
// `ArrayBuffer` | `Buffer` | `ArrayBufferView`
|
||||
return this.fromBuffer(value);
|
||||
}
|
||||
else {
|
||||
// `CRC32CValidator`/`CRC32C`-like
|
||||
return this.fromString(value.toString());
|
||||
}
|
||||
}
|
||||
}
|
||||
exports.CRC32C = CRC32C;
|
||||
_CRC32C_crc32c = new WeakMap();
|
||||
CRC32C.CRC32C_EXTENSIONS = CRC32C_EXTENSIONS;
|
||||
CRC32C.CRC32C_EXTENSION_TABLE = CRC32C_EXTENSION_TABLE;
|
||||
//# sourceMappingURL=crc32c.js.map
|
||||
@ -0,0 +1,852 @@
|
||||
/// <reference types="node" />
|
||||
/// <reference types="node" />
|
||||
/// <reference types="node" />
|
||||
/// <reference types="node" />
|
||||
import { BodyResponseCallback, DecorateRequestOptions, GetConfig, Metadata, MetadataCallback, ServiceObject, SetMetadataResponse } from './nodejs-common';
|
||||
import { Writable, Readable } from 'stream';
|
||||
import * as http from 'http';
|
||||
import { PreconditionOptions, Storage } from './storage';
|
||||
import { AvailableServiceObjectMethods, Bucket } from './bucket';
|
||||
import { Acl } from './acl';
|
||||
import { GetSignedUrlResponse, GetSignedUrlCallback, URLSigner, Query } from './signer';
|
||||
import { ResponseBody, Duplexify } from './nodejs-common/util';
|
||||
import { CRC32CValidatorGenerator } from './crc32c';
|
||||
import { URL } from 'url';
|
||||
import { DeleteCallback, DeleteOptions, SetMetadataOptions } from './nodejs-common/service-object';
|
||||
import * as r from 'teeny-request';
|
||||
export type GetExpirationDateResponse = [Date];
|
||||
export interface GetExpirationDateCallback {
|
||||
(err: Error | null, expirationDate?: Date | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export interface PolicyDocument {
|
||||
string: string;
|
||||
base64: string;
|
||||
signature: string;
|
||||
}
|
||||
export type GenerateSignedPostPolicyV2Response = [PolicyDocument];
|
||||
export interface GenerateSignedPostPolicyV2Callback {
|
||||
(err: Error | null, policy?: PolicyDocument): void;
|
||||
}
|
||||
export interface GenerateSignedPostPolicyV2Options {
|
||||
equals?: string[] | string[][];
|
||||
expires: string | number | Date;
|
||||
startsWith?: string[] | string[][];
|
||||
acl?: string;
|
||||
successRedirect?: string;
|
||||
successStatus?: string;
|
||||
contentLengthRange?: {
|
||||
min?: number;
|
||||
max?: number;
|
||||
};
|
||||
}
|
||||
export interface PolicyFields {
|
||||
[key: string]: string;
|
||||
}
|
||||
export interface GenerateSignedPostPolicyV4Options {
|
||||
expires: string | number | Date;
|
||||
bucketBoundHostname?: string;
|
||||
virtualHostedStyle?: boolean;
|
||||
conditions?: object[];
|
||||
fields?: PolicyFields;
|
||||
}
|
||||
export interface GenerateSignedPostPolicyV4Callback {
|
||||
(err: Error | null, output?: SignedPostPolicyV4Output): void;
|
||||
}
|
||||
export type GenerateSignedPostPolicyV4Response = [SignedPostPolicyV4Output];
|
||||
export interface SignedPostPolicyV4Output {
|
||||
url: string;
|
||||
fields: PolicyFields;
|
||||
}
|
||||
export interface GetSignedUrlConfig {
|
||||
action: 'read' | 'write' | 'delete' | 'resumable';
|
||||
version?: 'v2' | 'v4';
|
||||
virtualHostedStyle?: boolean;
|
||||
cname?: string;
|
||||
contentMd5?: string;
|
||||
contentType?: string;
|
||||
expires: string | number | Date;
|
||||
accessibleAt?: string | number | Date;
|
||||
extensionHeaders?: http.OutgoingHttpHeaders;
|
||||
promptSaveAs?: string;
|
||||
responseDisposition?: string;
|
||||
responseType?: string;
|
||||
queryParams?: Query;
|
||||
}
|
||||
export interface GetFileMetadataOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export type GetFileMetadataResponse = [Metadata, Metadata];
|
||||
export interface GetFileMetadataCallback {
|
||||
(err: Error | null, metadata?: Metadata, apiResponse?: Metadata): void;
|
||||
}
|
||||
export interface GetFileOptions extends GetConfig {
|
||||
userProject?: string;
|
||||
}
|
||||
export type GetFileResponse = [File, Metadata];
|
||||
export interface GetFileCallback {
|
||||
(err: Error | null, file?: File, apiResponse?: Metadata): void;
|
||||
}
|
||||
export interface FileExistsOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export type FileExistsResponse = [boolean];
|
||||
export interface FileExistsCallback {
|
||||
(err: Error | null, exists?: boolean): void;
|
||||
}
|
||||
export interface DeleteFileOptions {
|
||||
ignoreNotFound?: boolean;
|
||||
userProject?: string;
|
||||
}
|
||||
export type DeleteFileResponse = [Metadata];
|
||||
export interface DeleteFileCallback {
|
||||
(err: Error | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export type PredefinedAcl = 'authenticatedRead' | 'bucketOwnerFullControl' | 'bucketOwnerRead' | 'private' | 'projectPrivate' | 'publicRead';
|
||||
export interface CreateResumableUploadOptions {
|
||||
chunkSize?: number;
|
||||
highWaterMark?: number;
|
||||
metadata?: Metadata;
|
||||
origin?: string;
|
||||
offset?: number;
|
||||
predefinedAcl?: PredefinedAcl;
|
||||
private?: boolean;
|
||||
public?: boolean;
|
||||
uri?: string;
|
||||
userProject?: string;
|
||||
preconditionOpts?: PreconditionOptions;
|
||||
}
|
||||
export type CreateResumableUploadResponse = [string];
|
||||
export interface CreateResumableUploadCallback {
|
||||
(err: Error | null, uri?: string): void;
|
||||
}
|
||||
export interface CreateWriteStreamOptions extends CreateResumableUploadOptions {
|
||||
contentType?: string;
|
||||
gzip?: string | boolean;
|
||||
resumable?: boolean;
|
||||
timeout?: number;
|
||||
validation?: string | boolean;
|
||||
}
|
||||
export interface MakeFilePrivateOptions {
|
||||
metadata?: Metadata;
|
||||
strict?: boolean;
|
||||
userProject?: string;
|
||||
preconditionOpts?: PreconditionOptions;
|
||||
}
|
||||
export type MakeFilePrivateResponse = [Metadata];
|
||||
export type MakeFilePrivateCallback = SetFileMetadataCallback;
|
||||
export interface IsPublicCallback {
|
||||
(err: Error | null, resp?: boolean): void;
|
||||
}
|
||||
export type IsPublicResponse = [boolean];
|
||||
export type MakeFilePublicResponse = [Metadata];
|
||||
export interface MakeFilePublicCallback {
|
||||
(err?: Error | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export type MoveResponse = [Metadata];
|
||||
export interface MoveCallback {
|
||||
(err: Error | null, destinationFile?: File | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export interface MoveOptions {
|
||||
userProject?: string;
|
||||
preconditionOpts?: PreconditionOptions;
|
||||
}
|
||||
export type RenameOptions = MoveOptions;
|
||||
export type RenameResponse = MoveResponse;
|
||||
export type RenameCallback = MoveCallback;
|
||||
export type RotateEncryptionKeyOptions = string | Buffer | EncryptionKeyOptions;
|
||||
export interface EncryptionKeyOptions {
|
||||
encryptionKey?: string | Buffer;
|
||||
kmsKeyName?: string;
|
||||
preconditionOpts?: PreconditionOptions;
|
||||
}
|
||||
export type RotateEncryptionKeyCallback = CopyCallback;
|
||||
export type RotateEncryptionKeyResponse = CopyResponse;
|
||||
export declare enum ActionToHTTPMethod {
|
||||
read = "GET",
|
||||
write = "PUT",
|
||||
delete = "DELETE",
|
||||
resumable = "POST"
|
||||
}
|
||||
/**
|
||||
* @private
|
||||
*/
|
||||
export declare const STORAGE_POST_POLICY_BASE_URL = "https://storage.googleapis.com";
|
||||
export interface FileOptions {
|
||||
crc32cGenerator?: CRC32CValidatorGenerator;
|
||||
encryptionKey?: string | Buffer;
|
||||
generation?: number | string;
|
||||
kmsKeyName?: string;
|
||||
preconditionOpts?: PreconditionOptions;
|
||||
userProject?: string;
|
||||
}
|
||||
export interface CopyOptions {
|
||||
cacheControl?: string;
|
||||
contentEncoding?: string;
|
||||
contentType?: string;
|
||||
contentDisposition?: string;
|
||||
destinationKmsKeyName?: string;
|
||||
metadata?: Metadata;
|
||||
predefinedAcl?: string;
|
||||
token?: string;
|
||||
userProject?: string;
|
||||
preconditionOpts?: PreconditionOptions;
|
||||
}
|
||||
export type CopyResponse = [File, Metadata];
|
||||
export interface CopyCallback {
|
||||
(err: Error | null, file?: File | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export type DownloadResponse = [Buffer];
|
||||
export type DownloadCallback = (err: RequestError | null, contents: Buffer) => void;
|
||||
export interface DownloadOptions extends CreateReadStreamOptions {
|
||||
destination?: string;
|
||||
}
|
||||
export interface CreateReadStreamOptions {
|
||||
userProject?: string;
|
||||
validation?: 'md5' | 'crc32c' | false | true;
|
||||
start?: number;
|
||||
end?: number;
|
||||
decompress?: boolean;
|
||||
}
|
||||
export interface SaveOptions extends CreateWriteStreamOptions {
|
||||
onUploadProgress?: (progressEvent: any) => void;
|
||||
}
|
||||
export interface SaveCallback {
|
||||
(err?: Error | null): void;
|
||||
}
|
||||
export interface SetFileMetadataOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export interface SetFileMetadataCallback {
|
||||
(err?: Error | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export type SetFileMetadataResponse = [Metadata];
|
||||
export type SetStorageClassResponse = [Metadata];
|
||||
export interface SetStorageClassOptions {
|
||||
userProject?: string;
|
||||
preconditionOpts?: PreconditionOptions;
|
||||
}
|
||||
export interface SetStorageClassCallback {
|
||||
(err?: Error | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export declare class RequestError extends Error {
|
||||
code?: string;
|
||||
errors?: Error[];
|
||||
}
|
||||
export declare enum FileExceptionMessages {
|
||||
EXPIRATION_TIME_NA = "An expiration time is not available.",
|
||||
DESTINATION_NO_NAME = "Destination file should have a name.",
|
||||
INVALID_VALIDATION_FILE_RANGE = "Cannot use validation with file ranges (start/end).",
|
||||
MD5_NOT_AVAILABLE = "MD5 verification was specified, but is not available for the requested object. MD5 is not available for composite objects.",
|
||||
EQUALS_CONDITION_TWO_ELEMENTS = "Equals condition must be an array of 2 elements.",
|
||||
STARTS_WITH_TWO_ELEMENTS = "StartsWith condition must be an array of 2 elements.",
|
||||
CONTENT_LENGTH_RANGE_MIN_MAX = "ContentLengthRange must have numeric min & max fields.",
|
||||
DOWNLOAD_MISMATCH = "The downloaded data did not match the data from the server. To be sure the content is the same, you should download the file again.",
|
||||
UPLOAD_MISMATCH_DELETE_FAIL = "The uploaded data did not match the data from the server.\n As a precaution, we attempted to delete the file, but it was not successful.\n To be sure the content is the same, you should try removing the file manually,\n then uploading the file again.\n \n\nThe delete attempt failed with this message:\n\n ",
|
||||
UPLOAD_MISMATCH = "The uploaded data did not match the data from the server.\n As a precaution, the file has been deleted.\n To be sure the content is the same, you should try uploading the file again."
|
||||
}
|
||||
/**
|
||||
* A File object is created from your {@link Bucket} object using
|
||||
* {@link Bucket#file}.
|
||||
*
|
||||
* @class
|
||||
*/
|
||||
declare class File extends ServiceObject<File> {
|
||||
#private;
|
||||
acl: Acl;
|
||||
crc32cGenerator: CRC32CValidatorGenerator;
|
||||
bucket: Bucket;
|
||||
storage: Storage;
|
||||
kmsKeyName?: string;
|
||||
userProject?: string;
|
||||
signer?: URLSigner;
|
||||
metadata: Metadata;
|
||||
name: string;
|
||||
generation?: number;
|
||||
parent: Bucket;
|
||||
private encryptionKey?;
|
||||
private encryptionKeyBase64?;
|
||||
private encryptionKeyHash?;
|
||||
private encryptionKeyInterceptor?;
|
||||
private instanceRetryValue?;
|
||||
instancePreconditionOpts?: PreconditionOptions;
|
||||
/**
|
||||
* Cloud Storage uses access control lists (ACLs) to manage object and
|
||||
* bucket access. ACLs are the mechanism you use to share objects with other
|
||||
* users and allow other users to access your buckets and objects.
|
||||
*
|
||||
* An ACL consists of one or more entries, where each entry grants permissions
|
||||
* to an entity. Permissions define the actions that can be performed against
|
||||
* an object or bucket (for example, `READ` or `WRITE`); the entity defines
|
||||
* who the permission applies to (for example, a specific user or group of
|
||||
* users).
|
||||
*
|
||||
* The `acl` object on a File instance provides methods to get you a list of
|
||||
* the ACLs defined on your bucket, as well as set, update, and delete them.
|
||||
*
|
||||
* See {@link http://goo.gl/6qBBPO| About Access Control lists}
|
||||
*
|
||||
* @name File#acl
|
||||
* @mixes Acl
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
*
|
||||
* const file = myBucket.file('my-file');
|
||||
* //-
|
||||
* // Make a file publicly readable.
|
||||
* //-
|
||||
* const options = {
|
||||
* entity: 'allUsers',
|
||||
* role: storage.acl.READER_ROLE
|
||||
* };
|
||||
*
|
||||
* file.acl.add(options, function(err, aclObject) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* file.acl.add(options).then(function(data) {
|
||||
* const aclObject = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
/**
|
||||
* The API-formatted resource description of the file.
|
||||
*
|
||||
* Note: This is not guaranteed to be up-to-date when accessed. To get the
|
||||
* latest record, call the `getMetadata()` method.
|
||||
*
|
||||
* @name File#metadata
|
||||
* @type {object}
|
||||
*/
|
||||
/**
|
||||
* The file's name.
|
||||
* @name File#name
|
||||
* @type {string}
|
||||
*/
|
||||
/**
|
||||
* @callback Crc32cGeneratorToStringCallback
|
||||
* A method returning the CRC32C as a base64-encoded string.
|
||||
*
|
||||
* @returns {string}
|
||||
*
|
||||
* @example
|
||||
* Hashing the string 'data' should return 'rth90Q=='
|
||||
*
|
||||
* ```js
|
||||
* const buffer = Buffer.from('data');
|
||||
* crc32c.update(buffer);
|
||||
* crc32c.toString(); // 'rth90Q=='
|
||||
* ```
|
||||
**/
|
||||
/**
|
||||
* @callback Crc32cGeneratorValidateCallback
|
||||
* A method validating a base64-encoded CRC32C string.
|
||||
*
|
||||
* @param {string} [value] base64-encoded CRC32C string to validate
|
||||
* @returns {boolean}
|
||||
*
|
||||
* @example
|
||||
* Should return `true` if the value matches, `false` otherwise
|
||||
*
|
||||
* ```js
|
||||
* const buffer = Buffer.from('data');
|
||||
* crc32c.update(buffer);
|
||||
* crc32c.validate('DkjKuA=='); // false
|
||||
* crc32c.validate('rth90Q=='); // true
|
||||
* ```
|
||||
**/
|
||||
/**
|
||||
* @callback Crc32cGeneratorUpdateCallback
|
||||
* A method for passing `Buffer`s for CRC32C generation.
|
||||
*
|
||||
* @param {Buffer} [data] data to update CRC32C value with
|
||||
* @returns {undefined}
|
||||
*
|
||||
* @example
|
||||
* Hashing buffers from 'some ' and 'text\n'
|
||||
*
|
||||
* ```js
|
||||
* const buffer1 = Buffer.from('some ');
|
||||
* crc32c.update(buffer1);
|
||||
*
|
||||
* const buffer2 = Buffer.from('text\n');
|
||||
* crc32c.update(buffer2);
|
||||
*
|
||||
* crc32c.toString(); // 'DkjKuA=='
|
||||
* ```
|
||||
**/
|
||||
/**
|
||||
* @typedef {object} CRC32CValidator
|
||||
* @property {Crc32cGeneratorToStringCallback}
|
||||
* @property {Crc32cGeneratorValidateCallback}
|
||||
* @property {Crc32cGeneratorUpdateCallback}
|
||||
*/
|
||||
/**
|
||||
* @callback Crc32cGeneratorCallback
|
||||
* @returns {CRC32CValidator}
|
||||
*/
|
||||
/**
|
||||
* @typedef {object} FileOptions Options passed to the File constructor.
|
||||
* @property {string} [encryptionKey] A custom encryption key.
|
||||
* @property {number} [generation] Generation to scope the file to.
|
||||
* @property {string} [kmsKeyName] Cloud KMS Key used to encrypt this
|
||||
* object, if the object is encrypted by such a key. Limited availability;
|
||||
* usable only by enabled projects.
|
||||
* @property {string} [userProject] The ID of the project which will be
|
||||
* billed for all requests made from File object.
|
||||
* @property {Crc32cGeneratorCallback} [callback] A function that generates a CRC32C Validator. Defaults to {@link CRC32C}
|
||||
*/
|
||||
/**
|
||||
* Constructs a file object.
|
||||
*
|
||||
* @param {Bucket} bucket The Bucket instance this file is
|
||||
* attached to.
|
||||
* @param {string} name The name of the remote file.
|
||||
* @param {FileOptions} [options] Configuration options.
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
*
|
||||
* const file = myBucket.file('my-file');
|
||||
* ```
|
||||
*/
|
||||
constructor(bucket: Bucket, name: string, options?: FileOptions);
|
||||
/**
|
||||
* The object's Cloud Storage URI (`gs://`)
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
* const file = bucket.file('image.png');
|
||||
*
|
||||
* // `gs://my-bucket/image.png`
|
||||
* const href = file.cloudStorageURI.href;
|
||||
* ```
|
||||
*/
|
||||
get cloudStorageURI(): URL;
|
||||
/**
|
||||
* A helper method for determining if a request should be retried based on preconditions.
|
||||
* This should only be used for methods where the idempotency is determined by
|
||||
* `ifGenerationMatch`
|
||||
* @private
|
||||
*
|
||||
* A request should not be retried under the following conditions:
|
||||
* - if precondition option `ifGenerationMatch` is not set OR
|
||||
* - if `idempotencyStrategy` is set to `RetryNever`
|
||||
*/
|
||||
private shouldRetryBasedOnPreconditionAndIdempotencyStrat;
|
||||
copy(destination: string | Bucket | File, options?: CopyOptions): Promise<CopyResponse>;
|
||||
copy(destination: string | Bucket | File, callback: CopyCallback): void;
|
||||
copy(destination: string | Bucket | File, options: CopyOptions, callback: CopyCallback): void;
|
||||
/**
|
||||
* @typedef {object} CreateReadStreamOptions Configuration options for File#createReadStream.
|
||||
* @property {string} [userProject] The ID of the project which will be
|
||||
* billed for the request.
|
||||
* @property {string|boolean} [validation] Possible values: `"md5"`,
|
||||
* `"crc32c"`, or `false`. By default, data integrity is validated with a
|
||||
* CRC32c checksum. You may use MD5 if preferred, but that hash is not
|
||||
* supported for composite objects. An error will be raised if MD5 is
|
||||
* specified but is not available. You may also choose to skip validation
|
||||
* completely, however this is **not recommended**.
|
||||
* @property {number} [start] A byte offset to begin the file's download
|
||||
* from. Default is 0. NOTE: Byte ranges are inclusive; that is,
|
||||
* `options.start = 0` and `options.end = 999` represent the first 1000
|
||||
* bytes in a file or object. NOTE: when specifying a byte range, data
|
||||
* integrity is not available.
|
||||
* @property {number} [end] A byte offset to stop reading the file at.
|
||||
* NOTE: Byte ranges are inclusive; that is, `options.start = 0` and
|
||||
* `options.end = 999` represent the first 1000 bytes in a file or object.
|
||||
* NOTE: when specifying a byte range, data integrity is not available.
|
||||
* @property {boolean} [decompress=true] Disable auto decompression of the
|
||||
* received data. By default this option is set to `true`.
|
||||
* Applicable in cases where the data was uploaded with
|
||||
* `gzip: true` option. See {@link File#createWriteStream}.
|
||||
*/
|
||||
/**
|
||||
* Create a readable stream to read the contents of the remote file. It can be
|
||||
* piped to a writable stream or listened to for 'data' events to read a
|
||||
* file's contents.
|
||||
*
|
||||
* In the unlikely event there is a mismatch between what you downloaded and
|
||||
* the version in your Bucket, your error handler will receive an error with
|
||||
* code "CONTENT_DOWNLOAD_MISMATCH". If you receive this error, the best
|
||||
* recourse is to try downloading the file again.
|
||||
*
|
||||
* NOTE: Readable streams will emit the `end` event when the file is fully
|
||||
* downloaded.
|
||||
*
|
||||
* @param {CreateReadStreamOptions} [options] Configuration options.
|
||||
* @returns {ReadableStream}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* //-
|
||||
* // <h4>Downloading a File</h4>
|
||||
* //
|
||||
* // The example below demonstrates how we can reference a remote file, then
|
||||
* // pipe its contents to a local file. This is effectively creating a local
|
||||
* // backup of your remote data.
|
||||
* //-
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
*
|
||||
* const fs = require('fs');
|
||||
* const remoteFile = bucket.file('image.png');
|
||||
* const localFilename = '/Users/stephen/Photos/image.png';
|
||||
*
|
||||
* remoteFile.createReadStream()
|
||||
* .on('error', function(err) {})
|
||||
* .on('response', function(response) {
|
||||
* // Server connected and responded with the specified status and headers.
|
||||
* })
|
||||
* .on('end', function() {
|
||||
* // The file is fully downloaded.
|
||||
* })
|
||||
* .pipe(fs.createWriteStream(localFilename));
|
||||
*
|
||||
* //-
|
||||
* // To limit the downloaded data to only a byte range, pass an options
|
||||
* // object.
|
||||
* //-
|
||||
* const logFile = myBucket.file('access_log');
|
||||
* logFile.createReadStream({
|
||||
* start: 10000,
|
||||
* end: 20000
|
||||
* })
|
||||
* .on('error', function(err) {})
|
||||
* .pipe(fs.createWriteStream('/Users/stephen/logfile.txt'));
|
||||
*
|
||||
* //-
|
||||
* // To read a tail byte range, specify only `options.end` as a negative
|
||||
* // number.
|
||||
* //-
|
||||
* const logFile = myBucket.file('access_log');
|
||||
* logFile.createReadStream({
|
||||
* end: -100
|
||||
* })
|
||||
* .on('error', function(err) {})
|
||||
* .pipe(fs.createWriteStream('/Users/stephen/logfile.txt'));
|
||||
* ```
|
||||
*/
|
||||
createReadStream(options?: CreateReadStreamOptions): Readable;
|
||||
createResumableUpload(options?: CreateResumableUploadOptions): Promise<CreateResumableUploadResponse>;
|
||||
createResumableUpload(options: CreateResumableUploadOptions, callback: CreateResumableUploadCallback): void;
|
||||
createResumableUpload(callback: CreateResumableUploadCallback): void;
|
||||
/**
|
||||
* @typedef {object} CreateWriteStreamOptions Configuration options for File#createWriteStream().
|
||||
* @property {string} [contentType] Alias for
|
||||
* `options.metadata.contentType`. If set to `auto`, the file name is used
|
||||
* to determine the contentType.
|
||||
* @property {string|boolean} [gzip] If true, automatically gzip the file.
|
||||
* If set to `auto`, the contentType is used to determine if the file
|
||||
* should be gzipped. This will set `options.metadata.contentEncoding` to
|
||||
* `gzip` if necessary.
|
||||
* @property {object} [metadata] See the examples below or
|
||||
* {@link https://cloud.google.com/storage/docs/json_api/v1/objects/insert#request_properties_JSON| Objects: insert request body}
|
||||
* for more details.
|
||||
* @property {number} [offset] The starting byte of the upload stream, for
|
||||
* resuming an interrupted upload. Defaults to 0.
|
||||
* @property {string} [predefinedAcl] Apply a predefined set of access
|
||||
* controls to this object.
|
||||
*
|
||||
* Acceptable values are:
|
||||
* - **`authenticatedRead`** - Object owner gets `OWNER` access, and
|
||||
* `allAuthenticatedUsers` get `READER` access.
|
||||
*
|
||||
* - **`bucketOwnerFullControl`** - Object owner gets `OWNER` access, and
|
||||
* project team owners get `OWNER` access.
|
||||
*
|
||||
* - **`bucketOwnerRead`** - Object owner gets `OWNER` access, and project
|
||||
* team owners get `READER` access.
|
||||
*
|
||||
* - **`private`** - Object owner gets `OWNER` access.
|
||||
*
|
||||
* - **`projectPrivate`** - Object owner gets `OWNER` access, and project
|
||||
* team members get access according to their roles.
|
||||
*
|
||||
* - **`publicRead`** - Object owner gets `OWNER` access, and `allUsers`
|
||||
* get `READER` access.
|
||||
* @property {boolean} [private] Make the uploaded file private. (Alias for
|
||||
* `options.predefinedAcl = 'private'`)
|
||||
* @property {boolean} [public] Make the uploaded file public. (Alias for
|
||||
* `options.predefinedAcl = 'publicRead'`)
|
||||
* @property {boolean} [resumable] Force a resumable upload. NOTE: When
|
||||
* working with streams, the file format and size is unknown until it's
|
||||
* completely consumed. Because of this, it's best for you to be explicit
|
||||
* for what makes sense given your input.
|
||||
* @property {number} [timeout=60000] Set the HTTP request timeout in
|
||||
* milliseconds. This option is not available for resumable uploads.
|
||||
* Default: `60000`
|
||||
* @property {string} [uri] The URI for an already-created resumable
|
||||
* upload. See {@link File#createResumableUpload}.
|
||||
* @property {string} [userProject] The ID of the project which will be
|
||||
* billed for the request.
|
||||
* @property {string|boolean} [validation] Possible values: `"md5"`,
|
||||
* `"crc32c"`, or `false`. By default, data integrity is validated with a
|
||||
* CRC32c checksum. You may use MD5 if preferred, but that hash is not
|
||||
* supported for composite objects. An error will be raised if MD5 is
|
||||
* specified but is not available. You may also choose to skip validation
|
||||
* completely, however this is **not recommended**. In addition to specifying
|
||||
* validation type, providing `metadata.crc32c` or `metadata.md5Hash` will
|
||||
* cause the server to perform validation in addition to client validation.
|
||||
* NOTE: Validation is automatically skipped for objects that were
|
||||
* uploaded using the `gzip` option and have already compressed content.
|
||||
*/
|
||||
/**
|
||||
* Create a writable stream to overwrite the contents of the file in your
|
||||
* bucket.
|
||||
*
|
||||
* A File object can also be used to create files for the first time.
|
||||
*
|
||||
* Resumable uploads are automatically enabled and must be shut off explicitly
|
||||
* by setting `options.resumable` to `false`.
|
||||
*
|
||||
*
|
||||
* <p class="notice">
|
||||
* There is some overhead when using a resumable upload that can cause
|
||||
* noticeable performance degradation while uploading a series of small
|
||||
* files. When uploading files less than 10MB, it is recommended that the
|
||||
* resumable feature is disabled.
|
||||
* </p>
|
||||
*
|
||||
* NOTE: Writable streams will emit the `finish` event when the file is fully
|
||||
* uploaded.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/how-tos/upload| Upload Options (Simple or Resumable)}
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/objects/insert| Objects: insert API Documentation}
|
||||
*
|
||||
* @param {CreateWriteStreamOptions} [options] Configuration options.
|
||||
* @returns {WritableStream}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const fs = require('fs');
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
*
|
||||
* const file = myBucket.file('my-file');
|
||||
*
|
||||
* //-
|
||||
* // <h4>Uploading a File</h4>
|
||||
* //
|
||||
* // Now, consider a case where we want to upload a file to your bucket. You
|
||||
* // have the option of using {@link Bucket#upload}, but that is just
|
||||
* // a convenience method which will do the following.
|
||||
* //-
|
||||
* fs.createReadStream('/Users/stephen/Photos/birthday-at-the-zoo/panda.jpg')
|
||||
* .pipe(file.createWriteStream())
|
||||
* .on('error', function(err) {})
|
||||
* .on('finish', function() {
|
||||
* // The file upload is complete.
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // <h4>Uploading a File with gzip compression</h4>
|
||||
* //-
|
||||
* fs.createReadStream('/Users/stephen/site/index.html')
|
||||
* .pipe(file.createWriteStream({ gzip: true }))
|
||||
* .on('error', function(err) {})
|
||||
* .on('finish', function() {
|
||||
* // The file upload is complete.
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // Downloading the file with `createReadStream` will automatically decode
|
||||
* // the file.
|
||||
* //-
|
||||
*
|
||||
* //-
|
||||
* // <h4>Uploading a File with Metadata</h4>
|
||||
* //
|
||||
* // One last case you may run into is when you want to upload a file to your
|
||||
* // bucket and set its metadata at the same time. Like above, you can use
|
||||
* // {@link Bucket#upload} to do this, which is just a wrapper around
|
||||
* // the following.
|
||||
* //-
|
||||
* fs.createReadStream('/Users/stephen/Photos/birthday-at-the-zoo/panda.jpg')
|
||||
* .pipe(file.createWriteStream({
|
||||
* metadata: {
|
||||
* contentType: 'image/jpeg',
|
||||
* metadata: {
|
||||
* custom: 'metadata'
|
||||
* }
|
||||
* }
|
||||
* }))
|
||||
* .on('error', function(err) {})
|
||||
* .on('finish', function() {
|
||||
* // The file upload is complete.
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
createWriteStream(options?: CreateWriteStreamOptions): Writable;
|
||||
/**
|
||||
* Delete the object.
|
||||
*
|
||||
* @param {function=} callback - The callback function.
|
||||
* @param {?error} callback.err - An error returned while making this request.
|
||||
* @param {object} callback.apiResponse - The full API response.
|
||||
*/
|
||||
delete(options?: DeleteOptions): Promise<[r.Response]>;
|
||||
delete(options: DeleteOptions, callback: DeleteCallback): void;
|
||||
delete(callback: DeleteCallback): void;
|
||||
download(options?: DownloadOptions): Promise<DownloadResponse>;
|
||||
download(options: DownloadOptions, callback: DownloadCallback): void;
|
||||
download(callback: DownloadCallback): void;
|
||||
/**
|
||||
* The Storage API allows you to use a custom key for server-side encryption.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/encryption#customer-supplied| Customer-supplied Encryption Keys}
|
||||
*
|
||||
* @param {string|buffer} encryptionKey An AES-256 encryption key.
|
||||
* @returns {File}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const crypto = require('crypto');
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
*
|
||||
* const encryptionKey = crypto.randomBytes(32);
|
||||
*
|
||||
* const fileWithCustomEncryption = myBucket.file('my-file');
|
||||
* fileWithCustomEncryption.setEncryptionKey(encryptionKey);
|
||||
*
|
||||
* const fileWithoutCustomEncryption = myBucket.file('my-file');
|
||||
*
|
||||
* fileWithCustomEncryption.save('data', function(err) {
|
||||
* // Try to download with the File object that hasn't had
|
||||
* // `setEncryptionKey()` called:
|
||||
* fileWithoutCustomEncryption.download(function(err) {
|
||||
* // We will receive an error:
|
||||
* // err.message === 'Bad Request'
|
||||
*
|
||||
* // Try again with the File object we called `setEncryptionKey()` on:
|
||||
* fileWithCustomEncryption.download(function(err, contents) {
|
||||
* // contents.toString() === 'data'
|
||||
* });
|
||||
* });
|
||||
* });
|
||||
*
|
||||
* ```
|
||||
* @example <caption>include:samples/encryption.js</caption>
|
||||
* region_tag:storage_upload_encrypted_file
|
||||
* Example of uploading an encrypted file:
|
||||
*
|
||||
* @example <caption>include:samples/encryption.js</caption>
|
||||
* region_tag:storage_download_encrypted_file
|
||||
* Example of downloading an encrypted file:
|
||||
*/
|
||||
setEncryptionKey(encryptionKey: string | Buffer): this;
|
||||
getExpirationDate(): Promise<GetExpirationDateResponse>;
|
||||
getExpirationDate(callback: GetExpirationDateCallback): void;
|
||||
generateSignedPostPolicyV2(options: GenerateSignedPostPolicyV2Options): Promise<GenerateSignedPostPolicyV2Response>;
|
||||
generateSignedPostPolicyV2(options: GenerateSignedPostPolicyV2Options, callback: GenerateSignedPostPolicyV2Callback): void;
|
||||
generateSignedPostPolicyV2(callback: GenerateSignedPostPolicyV2Callback): void;
|
||||
generateSignedPostPolicyV4(options: GenerateSignedPostPolicyV4Options): Promise<GenerateSignedPostPolicyV4Response>;
|
||||
generateSignedPostPolicyV4(options: GenerateSignedPostPolicyV4Options, callback: GenerateSignedPostPolicyV4Callback): void;
|
||||
generateSignedPostPolicyV4(callback: GenerateSignedPostPolicyV4Callback): void;
|
||||
getSignedUrl(cfg: GetSignedUrlConfig): Promise<GetSignedUrlResponse>;
|
||||
getSignedUrl(cfg: GetSignedUrlConfig, callback: GetSignedUrlCallback): void;
|
||||
isPublic(): Promise<IsPublicResponse>;
|
||||
isPublic(callback: IsPublicCallback): void;
|
||||
makePrivate(options?: MakeFilePrivateOptions): Promise<MakeFilePrivateResponse>;
|
||||
makePrivate(callback: MakeFilePrivateCallback): void;
|
||||
makePrivate(options: MakeFilePrivateOptions, callback: MakeFilePrivateCallback): void;
|
||||
makePublic(): Promise<MakeFilePublicResponse>;
|
||||
makePublic(callback: MakeFilePublicCallback): void;
|
||||
/**
|
||||
* The public URL of this File
|
||||
* Use {@link File#makePublic} to enable anonymous access via the returned URL.
|
||||
*
|
||||
* @returns {string}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('albums');
|
||||
* const file = bucket.file('my-file');
|
||||
*
|
||||
* // publicUrl will be "https://storage.googleapis.com/albums/my-file"
|
||||
* const publicUrl = file.publicUrl();
|
||||
* ```
|
||||
*/
|
||||
publicUrl(): string;
|
||||
move(destination: string | Bucket | File, options?: MoveOptions): Promise<MoveResponse>;
|
||||
move(destination: string | Bucket | File, callback: MoveCallback): void;
|
||||
move(destination: string | Bucket | File, options: MoveOptions, callback: MoveCallback): void;
|
||||
rename(destinationFile: string | File, options?: RenameOptions): Promise<RenameResponse>;
|
||||
rename(destinationFile: string | File, callback: RenameCallback): void;
|
||||
rename(destinationFile: string | File, options: RenameOptions, callback: RenameCallback): void;
|
||||
request(reqOpts: DecorateRequestOptions): Promise<[ResponseBody, Metadata]>;
|
||||
request(reqOpts: DecorateRequestOptions, callback: BodyResponseCallback): void;
|
||||
rotateEncryptionKey(options?: RotateEncryptionKeyOptions): Promise<RotateEncryptionKeyResponse>;
|
||||
rotateEncryptionKey(callback: RotateEncryptionKeyCallback): void;
|
||||
rotateEncryptionKey(options: RotateEncryptionKeyOptions, callback: RotateEncryptionKeyCallback): void;
|
||||
save(data: string | Buffer, options?: SaveOptions): Promise<void>;
|
||||
save(data: string | Buffer, callback: SaveCallback): void;
|
||||
save(data: string | Buffer, options: SaveOptions, callback: SaveCallback): void;
|
||||
setMetadata(metadata: Metadata, options?: SetMetadataOptions): Promise<SetMetadataResponse>;
|
||||
setMetadata(metadata: Metadata, callback: MetadataCallback): void;
|
||||
setMetadata(metadata: Metadata, options: SetMetadataOptions, callback: MetadataCallback): void;
|
||||
setStorageClass(storageClass: string, options?: SetStorageClassOptions): Promise<SetStorageClassResponse>;
|
||||
setStorageClass(storageClass: string, options: SetStorageClassOptions, callback: SetStorageClassCallback): void;
|
||||
setStorageClass(storageClass: string, callback?: SetStorageClassCallback): void;
|
||||
/**
|
||||
* Set a user project to be billed for all requests made from this File
|
||||
* object.
|
||||
*
|
||||
* @param {string} userProject The user project.
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('albums');
|
||||
* const file = bucket.file('my-file');
|
||||
*
|
||||
* file.setUserProject('grape-spaceship-123');
|
||||
* ```
|
||||
*/
|
||||
setUserProject(userProject: string): void;
|
||||
/**
|
||||
* This creates a resumable-upload upload stream.
|
||||
*
|
||||
* @param {Duplexify} stream - Duplexify stream of data to pipe to the file.
|
||||
* @param {object=} options - Configuration object.
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
startResumableUpload_(dup: Duplexify, options: CreateResumableUploadOptions): void;
|
||||
/**
|
||||
* Takes a readable stream and pipes it to a remote file. Unlike
|
||||
* `startResumableUpload_`, which uses the resumable upload technique, this
|
||||
* method uses a simple upload (all or nothing).
|
||||
*
|
||||
* @param {Duplexify} dup - Duplexify stream of data to pipe to the file.
|
||||
* @param {object=} options - Configuration object.
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
startSimpleUpload_(dup: Duplexify, options?: CreateWriteStreamOptions): void;
|
||||
disableAutoRetryConditionallyIdempotent_(coreOpts: any, methodType: AvailableServiceObjectMethods, localPreconditionOptions?: PreconditionOptions): void;
|
||||
private getBufferFromReadable;
|
||||
}
|
||||
/**
|
||||
* Reference to the {@link File} class.
|
||||
* @name module:@google-cloud/storage.File
|
||||
* @see File
|
||||
*/
|
||||
export { File };
|
||||
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,31 @@
|
||||
/// <reference types="node" />
|
||||
/// <reference types="node" />
|
||||
import { Transform } from 'stream';
|
||||
import { CRC32CValidatorGenerator } from './crc32c';
|
||||
interface HashStreamValidatorOptions {
|
||||
/** Enables CRC32C calculation. To validate a provided value use `crc32cExpected`. */
|
||||
crc32c: boolean;
|
||||
/** Enables MD5 calculation. To validate a provided value use `md5Expected`. */
|
||||
md5: boolean;
|
||||
/** Set a custom CRC32C generator */
|
||||
crc32cGenerator: CRC32CValidatorGenerator;
|
||||
/** Sets the expected CRC32C value to verify once all data has been consumed. Also sets the `crc32c` option to `true` */
|
||||
crc32cExpected?: string;
|
||||
/** Sets the expected MD5 value to verify once all data has been consumed. Also sets the `md5` option to `true` */
|
||||
md5Expected?: string;
|
||||
/** Indicates whether or not to run a validation check or only update the hash values */
|
||||
updateHashesOnly?: boolean;
|
||||
}
|
||||
declare class HashStreamValidator extends Transform {
|
||||
#private;
|
||||
readonly crc32cEnabled: boolean;
|
||||
readonly md5Enabled: boolean;
|
||||
readonly crc32cExpected: string | undefined;
|
||||
readonly md5Expected: string | undefined;
|
||||
readonly updateHashesOnly: boolean;
|
||||
constructor(options?: Partial<HashStreamValidatorOptions>);
|
||||
_flush(callback: (error?: Error | null | undefined) => void): void;
|
||||
_transform(chunk: Buffer, encoding: BufferEncoding, callback: (e?: Error) => void): void;
|
||||
test(hash: 'crc32c' | 'md5', sum: Buffer | string): boolean;
|
||||
}
|
||||
export { HashStreamValidator, HashStreamValidatorOptions };
|
||||
@ -0,0 +1,108 @@
|
||||
"use strict";
|
||||
// Copyright 2022 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {
|
||||
if (kind === "m") throw new TypeError("Private method is not writable");
|
||||
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter");
|
||||
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it");
|
||||
return (kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;
|
||||
};
|
||||
var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
|
||||
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
|
||||
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
||||
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
||||
};
|
||||
var _HashStreamValidator_crc32cHash, _HashStreamValidator_md5Hash, _HashStreamValidator_md5Digest;
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.HashStreamValidator = void 0;
|
||||
const crypto_1 = require("crypto");
|
||||
const stream_1 = require("stream");
|
||||
const crc32c_1 = require("./crc32c");
|
||||
const file_1 = require("./file");
|
||||
class HashStreamValidator extends stream_1.Transform {
|
||||
constructor(options = {}) {
|
||||
super();
|
||||
this.updateHashesOnly = false;
|
||||
_HashStreamValidator_crc32cHash.set(this, undefined);
|
||||
_HashStreamValidator_md5Hash.set(this, undefined);
|
||||
_HashStreamValidator_md5Digest.set(this, '');
|
||||
this.crc32cEnabled = !!options.crc32c;
|
||||
this.md5Enabled = !!options.md5;
|
||||
this.updateHashesOnly = !!options.updateHashesOnly;
|
||||
this.crc32cExpected = options.crc32cExpected;
|
||||
this.md5Expected = options.md5Expected;
|
||||
if (this.crc32cEnabled) {
|
||||
const crc32cGenerator = options.crc32cGenerator || crc32c_1.CRC32C_DEFAULT_VALIDATOR_GENERATOR;
|
||||
__classPrivateFieldSet(this, _HashStreamValidator_crc32cHash, crc32cGenerator(), "f");
|
||||
}
|
||||
if (this.md5Enabled) {
|
||||
__classPrivateFieldSet(this, _HashStreamValidator_md5Hash, (0, crypto_1.createHash)('md5'), "f");
|
||||
}
|
||||
}
|
||||
_flush(callback) {
|
||||
if (__classPrivateFieldGet(this, _HashStreamValidator_md5Hash, "f")) {
|
||||
__classPrivateFieldSet(this, _HashStreamValidator_md5Digest, __classPrivateFieldGet(this, _HashStreamValidator_md5Hash, "f").digest('base64'), "f");
|
||||
}
|
||||
if (this.updateHashesOnly) {
|
||||
callback();
|
||||
return;
|
||||
}
|
||||
// If we're doing validation, assume the worst-- a data integrity
|
||||
// mismatch. If not, these tests won't be performed, and we can assume
|
||||
// the best.
|
||||
// We must check if the server decompressed the data on serve because hash
|
||||
// validation is not possible in this case.
|
||||
let failed = this.crc32cEnabled || this.md5Enabled;
|
||||
if (this.crc32cEnabled && this.crc32cExpected) {
|
||||
failed = !this.test('crc32c', this.crc32cExpected);
|
||||
}
|
||||
if (this.md5Enabled && this.md5Expected) {
|
||||
failed = !this.test('md5', this.md5Expected);
|
||||
}
|
||||
if (failed) {
|
||||
const mismatchError = new file_1.RequestError(file_1.FileExceptionMessages.DOWNLOAD_MISMATCH);
|
||||
mismatchError.code = 'CONTENT_DOWNLOAD_MISMATCH';
|
||||
callback(mismatchError);
|
||||
}
|
||||
else {
|
||||
callback();
|
||||
}
|
||||
}
|
||||
_transform(chunk, encoding, callback) {
|
||||
this.push(chunk, encoding);
|
||||
try {
|
||||
if (__classPrivateFieldGet(this, _HashStreamValidator_crc32cHash, "f"))
|
||||
__classPrivateFieldGet(this, _HashStreamValidator_crc32cHash, "f").update(chunk);
|
||||
if (__classPrivateFieldGet(this, _HashStreamValidator_md5Hash, "f"))
|
||||
__classPrivateFieldGet(this, _HashStreamValidator_md5Hash, "f").update(chunk);
|
||||
callback();
|
||||
}
|
||||
catch (e) {
|
||||
callback(e);
|
||||
}
|
||||
}
|
||||
test(hash, sum) {
|
||||
const check = Buffer.isBuffer(sum) ? sum.toString('base64') : sum;
|
||||
if (hash === 'crc32c' && __classPrivateFieldGet(this, _HashStreamValidator_crc32cHash, "f")) {
|
||||
return __classPrivateFieldGet(this, _HashStreamValidator_crc32cHash, "f").validate(check);
|
||||
}
|
||||
if (hash === 'md5' && __classPrivateFieldGet(this, _HashStreamValidator_md5Hash, "f")) {
|
||||
return __classPrivateFieldGet(this, _HashStreamValidator_md5Digest, "f") === check;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
exports.HashStreamValidator = HashStreamValidator;
|
||||
_HashStreamValidator_crc32cHash = new WeakMap(), _HashStreamValidator_md5Hash = new WeakMap(), _HashStreamValidator_md5Digest = new WeakMap();
|
||||
//# sourceMappingURL=hash-stream-validator.js.map
|
||||
@ -0,0 +1,95 @@
|
||||
import { Metadata, ServiceObject, MetadataCallback, SetMetadataResponse } from './nodejs-common';
|
||||
import { SetMetadataOptions } from './nodejs-common/service-object';
|
||||
import { Storage } from './storage';
|
||||
export interface HmacKeyOptions {
|
||||
projectId?: string;
|
||||
}
|
||||
export interface HmacKeyMetadata {
|
||||
accessId: string;
|
||||
etag?: string;
|
||||
id?: string;
|
||||
projectId?: string;
|
||||
serviceAccountEmail?: string;
|
||||
state?: string;
|
||||
timeCreated?: string;
|
||||
updated?: string;
|
||||
}
|
||||
export interface SetHmacKeyMetadataOptions {
|
||||
/**
|
||||
* This parameter is currently ignored.
|
||||
*/
|
||||
userProject?: string;
|
||||
}
|
||||
export interface SetHmacKeyMetadata {
|
||||
state?: 'ACTIVE' | 'INACTIVE';
|
||||
etag?: string;
|
||||
}
|
||||
export interface HmacKeyMetadataCallback {
|
||||
(err: Error | null, metadata?: HmacKeyMetadata, apiResponse?: Metadata): void;
|
||||
}
|
||||
export type HmacKeyMetadataResponse = [HmacKeyMetadata, Metadata];
|
||||
/**
|
||||
* The API-formatted resource description of the HMAC key.
|
||||
*
|
||||
* Note: This is not guaranteed to be up-to-date when accessed. To get the
|
||||
* latest record, call the `getMetadata()` method.
|
||||
*
|
||||
* @name HmacKey#metadata
|
||||
* @type {object}
|
||||
*/
|
||||
/**
|
||||
* An HmacKey object contains metadata of an HMAC key created from a
|
||||
* service account through the {@link Storage} client using
|
||||
* {@link Storage#createHmacKey}.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/authentication/hmackeys| HMAC keys documentation}
|
||||
*
|
||||
* @class
|
||||
*/
|
||||
export declare class HmacKey extends ServiceObject<HmacKeyMetadata | undefined> {
|
||||
metadata: HmacKeyMetadata | undefined;
|
||||
/**
|
||||
* A reference to the {@link Storage} associated with this {@link HmacKey}
|
||||
* instance.
|
||||
* @name HmacKey#storage
|
||||
* @type {Storage}
|
||||
*/
|
||||
storage: Storage;
|
||||
private instanceRetryValue?;
|
||||
/**
|
||||
* @typedef {object} HmacKeyOptions
|
||||
* @property {string} [projectId] The project ID of the project that owns
|
||||
* the service account of the requested HMAC key. If not provided,
|
||||
* the project ID used to instantiate the Storage client will be used.
|
||||
*/
|
||||
/**
|
||||
* Constructs an HmacKey object.
|
||||
*
|
||||
* Note: this only create a local reference to an HMAC key, to create
|
||||
* an HMAC key, use {@link Storage#createHmacKey}.
|
||||
*
|
||||
* @param {Storage} storage The Storage instance this HMAC key is
|
||||
* attached to.
|
||||
* @param {string} accessId The unique accessId for this HMAC key.
|
||||
* @param {HmacKeyOptions} options Constructor configurations.
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const hmacKey = storage.hmacKey('access-id');
|
||||
* ```
|
||||
*/
|
||||
constructor(storage: Storage, accessId: string, options?: HmacKeyOptions);
|
||||
/**
|
||||
* Set the metadata for this object.
|
||||
*
|
||||
* @param {object} metadata - The metadata to set on this object.
|
||||
* @param {object=} options - Configuration options.
|
||||
* @param {function=} callback - The callback function.
|
||||
* @param {?error} callback.err - An error returned while making this request.
|
||||
* @param {object} callback.apiResponse - The full API response.
|
||||
*/
|
||||
setMetadata(metadata: Metadata, options?: SetMetadataOptions): Promise<SetMetadataResponse>;
|
||||
setMetadata(metadata: Metadata, callback: MetadataCallback): void;
|
||||
setMetadata(metadata: Metadata, options: SetMetadataOptions, callback: MetadataCallback): void;
|
||||
}
|
||||
@ -0,0 +1,337 @@
|
||||
"use strict";
|
||||
// Copyright 2019 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.HmacKey = void 0;
|
||||
const nodejs_common_1 = require("./nodejs-common");
|
||||
const storage_1 = require("./storage");
|
||||
const promisify_1 = require("@google-cloud/promisify");
|
||||
/**
|
||||
* The API-formatted resource description of the HMAC key.
|
||||
*
|
||||
* Note: This is not guaranteed to be up-to-date when accessed. To get the
|
||||
* latest record, call the `getMetadata()` method.
|
||||
*
|
||||
* @name HmacKey#metadata
|
||||
* @type {object}
|
||||
*/
|
||||
/**
|
||||
* An HmacKey object contains metadata of an HMAC key created from a
|
||||
* service account through the {@link Storage} client using
|
||||
* {@link Storage#createHmacKey}.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/authentication/hmackeys| HMAC keys documentation}
|
||||
*
|
||||
* @class
|
||||
*/
|
||||
class HmacKey extends nodejs_common_1.ServiceObject {
|
||||
/**
|
||||
* @typedef {object} HmacKeyOptions
|
||||
* @property {string} [projectId] The project ID of the project that owns
|
||||
* the service account of the requested HMAC key. If not provided,
|
||||
* the project ID used to instantiate the Storage client will be used.
|
||||
*/
|
||||
/**
|
||||
* Constructs an HmacKey object.
|
||||
*
|
||||
* Note: this only create a local reference to an HMAC key, to create
|
||||
* an HMAC key, use {@link Storage#createHmacKey}.
|
||||
*
|
||||
* @param {Storage} storage The Storage instance this HMAC key is
|
||||
* attached to.
|
||||
* @param {string} accessId The unique accessId for this HMAC key.
|
||||
* @param {HmacKeyOptions} options Constructor configurations.
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const hmacKey = storage.hmacKey('access-id');
|
||||
* ```
|
||||
*/
|
||||
constructor(storage, accessId, options) {
|
||||
const methods = {
|
||||
/**
|
||||
* @typedef {object} DeleteHmacKeyOptions
|
||||
* @property {string} [userProject] This parameter is currently ignored.
|
||||
*/
|
||||
/**
|
||||
* @typedef {array} DeleteHmacKeyResponse
|
||||
* @property {object} 0 The full API response.
|
||||
*/
|
||||
/**
|
||||
* @callback DeleteHmacKeyCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
/**
|
||||
* Deletes an HMAC key.
|
||||
* Key state must be set to `INACTIVE` prior to deletion.
|
||||
* Caution: HMAC keys cannot be recovered once you delete them.
|
||||
*
|
||||
* The authenticated user must have `storage.hmacKeys.delete` permission for the project in which the key exists.
|
||||
*
|
||||
* @method HmacKey#delete
|
||||
* @param {DeleteHmacKeyOptions} [options] Configuration options.
|
||||
* @param {DeleteHmacKeyCallback} [callback] Callback function.
|
||||
* @returns {Promise<DeleteHmacKeyResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
*
|
||||
* //-
|
||||
* // Delete HMAC key after making the key inactive.
|
||||
* //-
|
||||
* const hmacKey = storage.hmacKey('ACCESS_ID');
|
||||
* hmacKey.setMetadata({state: 'INACTIVE'}, (err, hmacKeyMetadata) => {
|
||||
* if (err) {
|
||||
* // The request was an error.
|
||||
* console.error(err);
|
||||
* return;
|
||||
* }
|
||||
* hmacKey.delete((err) => {
|
||||
* if (err) {
|
||||
* console.error(err);
|
||||
* return;
|
||||
* }
|
||||
* // The HMAC key is deleted.
|
||||
* });
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, a promise is returned.
|
||||
* //-
|
||||
* const hmacKey = storage.hmacKey('ACCESS_ID');
|
||||
* hmacKey
|
||||
* .setMetadata({state: 'INACTIVE'})
|
||||
* .then(() => {
|
||||
* return hmacKey.delete();
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
delete: true,
|
||||
/**
|
||||
* @callback GetHmacKeyCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {HmacKey} hmacKey this {@link HmacKey} instance.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
/**
|
||||
* @typedef {array} GetHmacKeyResponse
|
||||
* @property {HmacKey} 0 This {@link HmacKey} instance.
|
||||
* @property {object} 1 The full API response.
|
||||
*/
|
||||
/**
|
||||
* @typedef {object} GetHmacKeyOptions
|
||||
* @property {string} [userProject] This parameter is currently ignored.
|
||||
*/
|
||||
/**
|
||||
* Retrieves and populate an HMAC key's metadata, and return
|
||||
* this {@link HmacKey} instance.
|
||||
*
|
||||
* HmacKey.get() does not give the HMAC key secret, as
|
||||
* it is only returned on creation.
|
||||
*
|
||||
* The authenticated user must have `storage.hmacKeys.get` permission
|
||||
* for the project in which the key exists.
|
||||
*
|
||||
* @method HmacKey#get
|
||||
* @param {GetHmacKeyOptions} [options] Configuration options.
|
||||
* @param {GetHmacKeyCallback} [callback] Callback function.
|
||||
* @returns {Promise<GetHmacKeyResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
*
|
||||
* //-
|
||||
* // Get the HmacKey's Metadata.
|
||||
* //-
|
||||
* storage.hmacKey('ACCESS_ID')
|
||||
* .get((err, hmacKey) => {
|
||||
* if (err) {
|
||||
* // The request was an error.
|
||||
* console.error(err);
|
||||
* return;
|
||||
* }
|
||||
* // do something with the returned HmacKey object.
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, a promise is returned.
|
||||
* //-
|
||||
* storage.hmacKey('ACCESS_ID')
|
||||
* .get()
|
||||
* .then((data) => {
|
||||
* const hmacKey = data[0];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
get: true,
|
||||
/**
|
||||
* @typedef {object} GetHmacKeyMetadataOptions
|
||||
* @property {string} [userProject] This parameter is currently ignored.
|
||||
*/
|
||||
/**
|
||||
* Retrieves and populate an HMAC key's metadata, and return
|
||||
* the HMAC key's metadata as an object.
|
||||
*
|
||||
* HmacKey.getMetadata() does not give the HMAC key secret, as
|
||||
* it is only returned on creation.
|
||||
*
|
||||
* The authenticated user must have `storage.hmacKeys.get` permission
|
||||
* for the project in which the key exists.
|
||||
*
|
||||
* @method HmacKey#getMetadata
|
||||
* @param {GetHmacKeyMetadataOptions} [options] Configuration options.
|
||||
* @param {HmacKeyMetadataCallback} [callback] Callback function.
|
||||
* @returns {Promise<HmacKeyMetadataResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
*
|
||||
* //-
|
||||
* // Get the HmacKey's metadata and populate to the metadata property.
|
||||
* //-
|
||||
* storage.hmacKey('ACCESS_ID')
|
||||
* .getMetadata((err, hmacKeyMetadata) => {
|
||||
* if (err) {
|
||||
* // The request was an error.
|
||||
* console.error(err);
|
||||
* return;
|
||||
* }
|
||||
* console.log(hmacKeyMetadata);
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, a promise is returned.
|
||||
* //-
|
||||
* storage.hmacKey('ACCESS_ID')
|
||||
* .getMetadata()
|
||||
* .then((data) => {
|
||||
* const hmacKeyMetadata = data[0];
|
||||
* console.log(hmacKeyMetadata);
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
getMetadata: true,
|
||||
/**
|
||||
* @typedef {object} SetHmacKeyMetadata Subset of {@link HmacKeyMetadata} to update.
|
||||
* @property {string} state New state of the HmacKey. Either 'ACTIVE' or 'INACTIVE'.
|
||||
* @property {string} [etag] Include an etag from a previous get HMAC key request
|
||||
* to perform safe read-modify-write.
|
||||
*/
|
||||
/**
|
||||
* @typedef {object} SetHmacKeyMetadataOptions
|
||||
* @property {string} [userProject] This parameter is currently ignored.
|
||||
*/
|
||||
/**
|
||||
* @callback HmacKeyMetadataCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {HmacKeyMetadata} metadata The updated {@link HmacKeyMetadata} object.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
/**
|
||||
* @typedef {array} HmacKeyMetadataResponse
|
||||
* @property {HmacKeyMetadata} 0 The updated {@link HmacKeyMetadata} object.
|
||||
* @property {object} 1 The full API response.
|
||||
*/
|
||||
/**
|
||||
* Updates the state of an HMAC key. See {@link SetHmacKeyMetadata} for
|
||||
* valid states.
|
||||
*
|
||||
* @method HmacKey#setMetadata
|
||||
* @param {SetHmacKeyMetadata} metadata The new metadata.
|
||||
* @param {SetHmacKeyMetadataOptions} [options] Configuration options.
|
||||
* @param {HmacKeyMetadataCallback} [callback] Callback function.
|
||||
* @returns {Promise<HmacKeyMetadataResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
*
|
||||
* const metadata = {
|
||||
* state: 'INACTIVE',
|
||||
* };
|
||||
*
|
||||
* storage.hmacKey('ACCESS_ID')
|
||||
* .setMetadata(metadata, (err, hmacKeyMetadata) => {
|
||||
* if (err) {
|
||||
* // The request was an error.
|
||||
* console.error(err);
|
||||
* return;
|
||||
* }
|
||||
* console.log(hmacKeyMetadata);
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, a promise is returned.
|
||||
* //-
|
||||
* storage.hmacKey('ACCESS_ID')
|
||||
* .setMetadata(metadata)
|
||||
* .then((data) => {
|
||||
* const hmacKeyMetadata = data[0];
|
||||
* console.log(hmacKeyMetadata);
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
setMetadata: {
|
||||
reqOpts: {
|
||||
method: 'PUT',
|
||||
},
|
||||
},
|
||||
};
|
||||
const projectId = (options && options.projectId) || storage.projectId;
|
||||
super({
|
||||
parent: storage,
|
||||
id: accessId,
|
||||
baseUrl: `/projects/${projectId}/hmacKeys`,
|
||||
methods,
|
||||
});
|
||||
this.storage = storage;
|
||||
this.instanceRetryValue = storage.retryOptions.autoRetry;
|
||||
}
|
||||
setMetadata(metadata, optionsOrCallback, cb) {
|
||||
// ETag preconditions are not currently supported. Retries should be disabled if the idempotency strategy is not set to RetryAlways
|
||||
if (this.storage.retryOptions.idempotencyStrategy !==
|
||||
storage_1.IdempotencyStrategy.RetryAlways) {
|
||||
this.storage.retryOptions.autoRetry = false;
|
||||
}
|
||||
const options = typeof optionsOrCallback === 'object' ? optionsOrCallback : {};
|
||||
cb =
|
||||
typeof optionsOrCallback === 'function'
|
||||
? optionsOrCallback
|
||||
: cb;
|
||||
super
|
||||
.setMetadata(metadata, options)
|
||||
.then(resp => cb(null, ...resp))
|
||||
.catch(cb)
|
||||
.finally(() => {
|
||||
this.storage.retryOptions.autoRetry = this.instanceRetryValue;
|
||||
});
|
||||
}
|
||||
}
|
||||
exports.HmacKey = HmacKey;
|
||||
/*! Developer Documentation
|
||||
*
|
||||
* All async methods (except for streams) will return a Promise in the event
|
||||
* that a callback is omitted.
|
||||
*/
|
||||
(0, promisify_1.promisifyAll)(HmacKey);
|
||||
//# sourceMappingURL=hmacKey.js.map
|
||||
@ -0,0 +1,118 @@
|
||||
import { Metadata } from './nodejs-common';
|
||||
import { Bucket } from './bucket';
|
||||
export interface GetPolicyOptions {
|
||||
userProject?: string;
|
||||
requestedPolicyVersion?: number;
|
||||
}
|
||||
export type GetPolicyResponse = [Policy, Metadata];
|
||||
/**
|
||||
* @callback GetPolicyCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {object} acl The policy.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
export interface GetPolicyCallback {
|
||||
(err?: Error | null, acl?: Policy, apiResponse?: Metadata): void;
|
||||
}
|
||||
/**
|
||||
* @typedef {object} SetPolicyOptions
|
||||
* @param {string} [userProject] The ID of the project which will be
|
||||
* billed for the request.
|
||||
*/
|
||||
export interface SetPolicyOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
/**
|
||||
* @typedef {array} SetPolicyResponse
|
||||
* @property {object} 0 The policy.
|
||||
* @property {object} 1 The full API response.
|
||||
*/
|
||||
export type SetPolicyResponse = [Policy, Metadata];
|
||||
/**
|
||||
* @callback SetPolicyCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {object} acl The policy.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
export interface SetPolicyCallback {
|
||||
(err?: Error | null, acl?: Policy, apiResponse?: object): void;
|
||||
}
|
||||
export interface Policy {
|
||||
bindings: PolicyBinding[];
|
||||
version?: number;
|
||||
etag?: string;
|
||||
}
|
||||
export interface PolicyBinding {
|
||||
role: string;
|
||||
members: string[];
|
||||
condition?: Expr;
|
||||
}
|
||||
export interface Expr {
|
||||
title?: string;
|
||||
description?: string;
|
||||
expression: string;
|
||||
}
|
||||
/**
|
||||
* @typedef {array} TestIamPermissionsResponse
|
||||
* @property {object} 0 A subset of permissions that the caller is allowed.
|
||||
* @property {object} 1 The full API response.
|
||||
*/
|
||||
export type TestIamPermissionsResponse = [{
|
||||
[key: string]: boolean;
|
||||
}, Metadata];
|
||||
/**
|
||||
* @callback TestIamPermissionsCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {object} acl A subset of permissions that the caller is allowed.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
export interface TestIamPermissionsCallback {
|
||||
(err?: Error | null, acl?: {
|
||||
[key: string]: boolean;
|
||||
} | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
/**
|
||||
* @typedef {object} TestIamPermissionsOptions Configuration options for Iam#testPermissions().
|
||||
* @param {string} [userProject] The ID of the project which will be
|
||||
* billed for the request.
|
||||
*/
|
||||
export interface TestIamPermissionsOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export declare enum IAMExceptionMessages {
|
||||
POLICY_OBJECT_REQUIRED = "A policy object is required.",
|
||||
PERMISSIONS_REQUIRED = "Permissions are required."
|
||||
}
|
||||
/**
|
||||
* Get and set IAM policies for your Cloud Storage bucket.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/access-control/iam#short_title_iam_management| Cloud Storage IAM Management}
|
||||
* See {@link https://cloud.google.com/iam/docs/granting-changing-revoking-access| Granting, Changing, and Revoking Access}
|
||||
* See {@link https://cloud.google.com/iam/docs/understanding-roles| IAM Roles}
|
||||
*
|
||||
* @constructor Iam
|
||||
*
|
||||
* @param {Bucket} bucket The parent instance.
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
* // bucket.iam
|
||||
* ```
|
||||
*/
|
||||
declare class Iam {
|
||||
private request_;
|
||||
private resourceId_;
|
||||
constructor(bucket: Bucket);
|
||||
getPolicy(options?: GetPolicyOptions): Promise<GetPolicyResponse>;
|
||||
getPolicy(options: GetPolicyOptions, callback: GetPolicyCallback): void;
|
||||
getPolicy(callback: GetPolicyCallback): void;
|
||||
setPolicy(policy: Policy, options?: SetPolicyOptions): Promise<SetPolicyResponse>;
|
||||
setPolicy(policy: Policy, callback: SetPolicyCallback): void;
|
||||
setPolicy(policy: Policy, options: SetPolicyOptions, callback: SetPolicyCallback): void;
|
||||
testPermissions(permissions: string | string[], options?: TestIamPermissionsOptions): Promise<TestIamPermissionsResponse>;
|
||||
testPermissions(permissions: string | string[], callback: TestIamPermissionsCallback): void;
|
||||
testPermissions(permissions: string | string[], options: TestIamPermissionsOptions, callback: TestIamPermissionsCallback): void;
|
||||
}
|
||||
export { Iam };
|
||||
@ -0,0 +1,307 @@
|
||||
"use strict";
|
||||
// Copyright 2019 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.Iam = exports.IAMExceptionMessages = void 0;
|
||||
const promisify_1 = require("@google-cloud/promisify");
|
||||
const util_1 = require("./util");
|
||||
var IAMExceptionMessages;
|
||||
(function (IAMExceptionMessages) {
|
||||
IAMExceptionMessages["POLICY_OBJECT_REQUIRED"] = "A policy object is required.";
|
||||
IAMExceptionMessages["PERMISSIONS_REQUIRED"] = "Permissions are required.";
|
||||
})(IAMExceptionMessages = exports.IAMExceptionMessages || (exports.IAMExceptionMessages = {}));
|
||||
/**
|
||||
* Get and set IAM policies for your Cloud Storage bucket.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/access-control/iam#short_title_iam_management| Cloud Storage IAM Management}
|
||||
* See {@link https://cloud.google.com/iam/docs/granting-changing-revoking-access| Granting, Changing, and Revoking Access}
|
||||
* See {@link https://cloud.google.com/iam/docs/understanding-roles| IAM Roles}
|
||||
*
|
||||
* @constructor Iam
|
||||
*
|
||||
* @param {Bucket} bucket The parent instance.
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
* // bucket.iam
|
||||
* ```
|
||||
*/
|
||||
class Iam {
|
||||
constructor(bucket) {
|
||||
this.request_ = bucket.request.bind(bucket);
|
||||
this.resourceId_ = 'buckets/' + bucket.getId();
|
||||
}
|
||||
/**
|
||||
* @typedef {object} GetPolicyOptions Requested options for IAM#getPolicy().
|
||||
* @property {number} [requestedPolicyVersion] The version of IAM policies to
|
||||
* request. If a policy with a condition is requested without setting
|
||||
* this, the server will return an error. This must be set to a value
|
||||
* of 3 to retrieve IAM policies containing conditions. This is to
|
||||
* prevent client code that isn't aware of IAM conditions from
|
||||
* interpreting and modifying policies incorrectly. The service might
|
||||
* return a policy with version lower than the one that was requested,
|
||||
* based on the feature syntax in the policy fetched.
|
||||
* See {@link https://cloud.google.com/iam/docs/policies#versions| IAM Policy versions}
|
||||
* @property {string} [userProject] The ID of the project which will be
|
||||
* billed for the request.
|
||||
*/
|
||||
/**
|
||||
* @typedef {array} GetPolicyResponse
|
||||
* @property {Policy} 0 The policy.
|
||||
* @property {object} 1 The full API response.
|
||||
*/
|
||||
/**
|
||||
* @typedef {object} Policy
|
||||
* @property {PolicyBinding[]} policy.bindings Bindings associate members with roles.
|
||||
* @property {string} [policy.etag] Etags are used to perform a read-modify-write.
|
||||
* @property {number} [policy.version] The syntax schema version of the Policy.
|
||||
* To set an IAM policy with conditional binding, this field must be set to
|
||||
* 3 or greater.
|
||||
* See {@link https://cloud.google.com/iam/docs/policies#versions| IAM Policy versions}
|
||||
*/
|
||||
/**
|
||||
* @typedef {object} PolicyBinding
|
||||
* @property {string} role Role that is assigned to members.
|
||||
* @property {string[]} members Specifies the identities requesting access for the bucket.
|
||||
* @property {Expr} [condition] The condition that is associated with this binding.
|
||||
*/
|
||||
/**
|
||||
* @typedef {object} Expr
|
||||
* @property {string} [title] An optional title for the expression, i.e. a
|
||||
* short string describing its purpose. This can be used e.g. in UIs
|
||||
* which allow to enter the expression.
|
||||
* @property {string} [description] An optional description of the
|
||||
* expression. This is a longer text which describes the expression,
|
||||
* e.g. when hovered over it in a UI.
|
||||
* @property {string} expression Textual representation of an expression in
|
||||
* Common Expression Language syntax. The application context of the
|
||||
* containing message determines which well-known feature set of CEL
|
||||
* is supported.The condition that is associated with this binding.
|
||||
*
|
||||
* @see [Condition] https://cloud.google.com/storage/docs/access-control/iam#conditions
|
||||
*/
|
||||
/**
|
||||
* Get the IAM policy.
|
||||
*
|
||||
* @param {GetPolicyOptions} [options] Request options.
|
||||
* @param {GetPolicyCallback} [callback] Callback function.
|
||||
* @returns {Promise<GetPolicyResponse>}
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/buckets/getIamPolicy| Buckets: setIamPolicy API Documentation}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
*
|
||||
* bucket.iam.getPolicy(
|
||||
* {requestedPolicyVersion: 3},
|
||||
* function(err, policy, apiResponse) {
|
||||
*
|
||||
* },
|
||||
* );
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* bucket.iam.getPolicy({requestedPolicyVersion: 3})
|
||||
* .then(function(data) {
|
||||
* const policy = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
*
|
||||
* ```
|
||||
* @example <caption>include:samples/iam.js</caption>
|
||||
* region_tag:storage_view_bucket_iam_members
|
||||
* Example of retrieving a bucket's IAM policy:
|
||||
*/
|
||||
getPolicy(optionsOrCallback, callback) {
|
||||
const { options, callback: cb } = (0, util_1.normalize)(optionsOrCallback, callback);
|
||||
const qs = {};
|
||||
if (options.userProject) {
|
||||
qs.userProject = options.userProject;
|
||||
}
|
||||
if (options.requestedPolicyVersion !== null &&
|
||||
options.requestedPolicyVersion !== undefined) {
|
||||
qs.optionsRequestedPolicyVersion = options.requestedPolicyVersion;
|
||||
}
|
||||
this.request_({
|
||||
uri: '/iam',
|
||||
qs,
|
||||
}, cb);
|
||||
}
|
||||
/**
|
||||
* Set the IAM policy.
|
||||
*
|
||||
* @throws {Error} If no policy is provided.
|
||||
*
|
||||
* @param {Policy} policy The policy.
|
||||
* @param {SetPolicyOptions} [options] Configuration options.
|
||||
* @param {SetPolicyCallback} callback Callback function.
|
||||
* @returns {Promise<SetPolicyResponse>}
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/buckets/setIamPolicy| Buckets: setIamPolicy API Documentation}
|
||||
* See {@link https://cloud.google.com/iam/docs/understanding-roles| IAM Roles}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
*
|
||||
* const myPolicy = {
|
||||
* bindings: [
|
||||
* {
|
||||
* role: 'roles/storage.admin',
|
||||
* members:
|
||||
* ['serviceAccount:myotherproject@appspot.gserviceaccount.com']
|
||||
* }
|
||||
* ]
|
||||
* };
|
||||
*
|
||||
* bucket.iam.setPolicy(myPolicy, function(err, policy, apiResponse) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* bucket.iam.setPolicy(myPolicy).then(function(data) {
|
||||
* const policy = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
*
|
||||
* ```
|
||||
* @example <caption>include:samples/iam.js</caption>
|
||||
* region_tag:storage_add_bucket_iam_member
|
||||
* Example of adding to a bucket's IAM policy:
|
||||
*
|
||||
* @example <caption>include:samples/iam.js</caption>
|
||||
* region_tag:storage_remove_bucket_iam_member
|
||||
* Example of removing from a bucket's IAM policy:
|
||||
*/
|
||||
setPolicy(policy, optionsOrCallback, callback) {
|
||||
if (policy === null || typeof policy !== 'object') {
|
||||
throw new Error(IAMExceptionMessages.POLICY_OBJECT_REQUIRED);
|
||||
}
|
||||
const { options, callback: cb } = (0, util_1.normalize)(optionsOrCallback, callback);
|
||||
let maxRetries;
|
||||
if (policy.etag === undefined) {
|
||||
maxRetries = 0;
|
||||
}
|
||||
this.request_({
|
||||
method: 'PUT',
|
||||
uri: '/iam',
|
||||
maxRetries,
|
||||
json: Object.assign({
|
||||
resourceId: this.resourceId_,
|
||||
}, policy),
|
||||
qs: options,
|
||||
}, cb);
|
||||
}
|
||||
/**
|
||||
* Test a set of permissions for a resource.
|
||||
*
|
||||
* @throws {Error} If permissions are not provided.
|
||||
*
|
||||
* @param {string|string[]} permissions The permission(s) to test for.
|
||||
* @param {TestIamPermissionsOptions} [options] Configuration object.
|
||||
* @param {TestIamPermissionsCallback} [callback] Callback function.
|
||||
* @returns {Promise<TestIamPermissionsResponse>}
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/buckets/testIamPermissions| Buckets: testIamPermissions API Documentation}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
*
|
||||
* //-
|
||||
* // Test a single permission.
|
||||
* //-
|
||||
* const test = 'storage.buckets.delete';
|
||||
*
|
||||
* bucket.iam.testPermissions(test, function(err, permissions, apiResponse) {
|
||||
* console.log(permissions);
|
||||
* // {
|
||||
* // "storage.buckets.delete": true
|
||||
* // }
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // Test several permissions at once.
|
||||
* //-
|
||||
* const tests = [
|
||||
* 'storage.buckets.delete',
|
||||
* 'storage.buckets.get'
|
||||
* ];
|
||||
*
|
||||
* bucket.iam.testPermissions(tests, function(err, permissions) {
|
||||
* console.log(permissions);
|
||||
* // {
|
||||
* // "storage.buckets.delete": false,
|
||||
* // "storage.buckets.get": true
|
||||
* // }
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* bucket.iam.testPermissions(test).then(function(data) {
|
||||
* const permissions = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
testPermissions(permissions, optionsOrCallback, callback) {
|
||||
if (!Array.isArray(permissions) && typeof permissions !== 'string') {
|
||||
throw new Error(IAMExceptionMessages.PERMISSIONS_REQUIRED);
|
||||
}
|
||||
const { options, callback: cb } = (0, util_1.normalize)(optionsOrCallback, callback);
|
||||
const permissionsArray = Array.isArray(permissions)
|
||||
? permissions
|
||||
: [permissions];
|
||||
const req = Object.assign({
|
||||
permissions: permissionsArray,
|
||||
}, options);
|
||||
this.request_({
|
||||
uri: '/iam/testPermissions',
|
||||
qs: req,
|
||||
useQuerystring: true,
|
||||
}, (err, resp) => {
|
||||
if (err) {
|
||||
cb(err, null, resp);
|
||||
return;
|
||||
}
|
||||
const availablePermissions = Array.isArray(resp.permissions)
|
||||
? resp.permissions
|
||||
: [];
|
||||
const permissionsHash = permissionsArray.reduce((acc, permission) => {
|
||||
acc[permission] = availablePermissions.indexOf(permission) > -1;
|
||||
return acc;
|
||||
}, {});
|
||||
cb(null, permissionsHash, resp);
|
||||
});
|
||||
}
|
||||
}
|
||||
exports.Iam = Iam;
|
||||
/*! Developer Documentation
|
||||
*
|
||||
* All async methods (except for streams) will return a Promise in the event
|
||||
* that a callback is omitted.
|
||||
*/
|
||||
(0, promisify_1.promisifyAll)(Iam);
|
||||
//# sourceMappingURL=iam.js.map
|
||||
@ -0,0 +1,56 @@
|
||||
/**
|
||||
* The `@google-cloud/storage` package has a single named export which is the
|
||||
* {@link Storage} (ES6) class, which should be instantiated with `new`.
|
||||
*
|
||||
* See {@link Storage} and {@link ClientConfig} for client methods and
|
||||
* configuration options.
|
||||
*
|
||||
* @module {Storage} @google-cloud/storage
|
||||
* @alias nodejs-storage
|
||||
*
|
||||
* @example
|
||||
* Install the client library with <a href="https://www.npmjs.com/">npm</a>:
|
||||
* ```
|
||||
* npm install --save @google-cloud/storage
|
||||
* ```
|
||||
*
|
||||
* @example
|
||||
* Import the client library
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* ```
|
||||
*
|
||||
* @example
|
||||
* Create a client that uses <a
|
||||
* href="https://cloud.google.com/docs/authentication/production#providing_credentials_to_your_application">Application
|
||||
* Default Credentials (ADC)</a>:
|
||||
* ```
|
||||
* const storage = new Storage();
|
||||
* ```
|
||||
*
|
||||
* @example
|
||||
* Create a client with <a
|
||||
* href="https://cloud.google.com/docs/authentication/production#obtaining_and_providing_service_account_credentials_manually">explicit
|
||||
* credentials</a>:
|
||||
* ```
|
||||
* const storage = new Storage({ projectId:
|
||||
* 'your-project-id', keyFilename: '/path/to/keyfile.json'
|
||||
* });
|
||||
* ```
|
||||
*
|
||||
* @example <caption>include:samples/quickstart.js</caption>
|
||||
* region_tag:storage_quickstart
|
||||
* Full quickstart example:
|
||||
*/
|
||||
export { AccessControlObject, AclOptions, AddAclCallback, AddAclOptions, AddAclResponse, GetAclCallback, GetAclOptions, GetAclResponse, RemoveAclCallback, RemoveAclOptions, RemoveAclResponse, UpdateAclCallback, UpdateAclOptions, UpdateAclResponse, } from './acl';
|
||||
export { Bucket, BucketExistsCallback, BucketExistsOptions, BucketExistsResponse, BucketLockCallback, BucketLockResponse, CombineCallback, CombineOptions, CombineResponse, CreateChannelCallback, CreateChannelConfig, CreateChannelOptions, CreateChannelResponse, CreateNotificationCallback, CreateNotificationOptions, CreateNotificationResponse, DeleteBucketCallback, DeleteBucketOptions, DeleteBucketResponse, DeleteFilesCallback, DeleteFilesOptions, DeleteLabelsCallback, DeleteLabelsResponse, DisableRequesterPaysCallback, DisableRequesterPaysResponse, EnableRequesterPaysCallback, EnableRequesterPaysResponse, GetBucketCallback, GetBucketMetadataCallback, GetBucketMetadataOptions, GetBucketMetadataResponse, GetBucketOptions, GetBucketResponse, GetBucketSignedUrlConfig, GetFilesCallback, GetFilesOptions, GetFilesResponse, GetLabelsCallback, GetLabelsOptions, GetLabelsResponse, GetNotificationsCallback, GetNotificationsOptions, GetNotificationsResponse, Labels, MakeBucketPrivateCallback, MakeBucketPrivateOptions, MakeBucketPrivateResponse, MakeBucketPublicCallback, MakeBucketPublicOptions, MakeBucketPublicResponse, SetBucketMetadataCallback, SetBucketMetadataOptions, SetBucketMetadataResponse, SetBucketStorageClassCallback, SetBucketStorageClassOptions, SetLabelsCallback, SetLabelsOptions, SetLabelsResponse, UploadCallback, UploadOptions, UploadResponse, } from './bucket';
|
||||
export * from './crc32c';
|
||||
export { Channel, StopCallback } from './channel';
|
||||
export { CopyCallback, CopyOptions, CopyResponse, CreateReadStreamOptions, CreateResumableUploadCallback, CreateResumableUploadOptions, CreateResumableUploadResponse, CreateWriteStreamOptions, DeleteFileCallback, DeleteFileOptions, DeleteFileResponse, DownloadCallback, DownloadOptions, DownloadResponse, EncryptionKeyOptions, File, FileExistsCallback, FileExistsOptions, FileExistsResponse, FileOptions, GetExpirationDateCallback, GetExpirationDateResponse, GetFileCallback, GetFileMetadataCallback, GetFileMetadataOptions, GetFileMetadataResponse, GetFileOptions, GetFileResponse, GenerateSignedPostPolicyV2Callback, GenerateSignedPostPolicyV2Options, GenerateSignedPostPolicyV2Response, GenerateSignedPostPolicyV4Callback, GenerateSignedPostPolicyV4Options, GenerateSignedPostPolicyV4Response, GetSignedUrlConfig, MakeFilePrivateCallback, MakeFilePrivateOptions, MakeFilePrivateResponse, MakeFilePublicCallback, MakeFilePublicResponse, MoveCallback, MoveOptions, MoveResponse, PolicyDocument, PolicyFields, PredefinedAcl, RotateEncryptionKeyCallback, RotateEncryptionKeyOptions, RotateEncryptionKeyResponse, SaveCallback, SaveOptions, SetFileMetadataCallback, SetFileMetadataOptions, SetFileMetadataResponse, SetStorageClassCallback, SetStorageClassOptions, SetStorageClassResponse, SignedPostPolicyV4Output, } from './file';
|
||||
export * from './hash-stream-validator';
|
||||
export { HmacKey, HmacKeyMetadata, HmacKeyMetadataCallback, HmacKeyMetadataResponse, SetHmacKeyMetadata, SetHmacKeyMetadataOptions, } from './hmacKey';
|
||||
export { GetPolicyCallback, GetPolicyOptions, GetPolicyResponse, Iam, Policy, SetPolicyCallback, SetPolicyOptions, SetPolicyResponse, TestIamPermissionsCallback, TestIamPermissionsOptions, TestIamPermissionsResponse, } from './iam';
|
||||
export { DeleteNotificationCallback, DeleteNotificationOptions, GetNotificationCallback, GetNotificationMetadataCallback, GetNotificationMetadataOptions, GetNotificationMetadataResponse, GetNotificationOptions, GetNotificationResponse, Notification, } from './notification';
|
||||
export { BucketCallback, BucketOptions, CreateBucketQuery, CreateBucketRequest, CreateBucketResponse, CreateHmacKeyCallback, CreateHmacKeyOptions, CreateHmacKeyResponse, GetBucketsCallback, GetBucketsRequest, GetBucketsResponse, GetHmacKeysCallback, GetHmacKeysOptions, GetHmacKeysResponse, GetServiceAccountCallback, GetServiceAccountOptions, GetServiceAccountResponse, HmacKeyResourceResponse, IdempotencyStrategy, PreconditionOptions, ServiceAccount, Storage, StorageOptions, } from './storage';
|
||||
export { GetSignedUrlCallback, GetSignedUrlResponse } from './signer';
|
||||
export * from './transfer-manager';
|
||||
@ -0,0 +1,49 @@
|
||||
"use strict";
|
||||
// Copyright 2019 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
||||
if (k2 === undefined) k2 = k;
|
||||
var desc = Object.getOwnPropertyDescriptor(m, k);
|
||||
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
||||
desc = { enumerable: true, get: function() { return m[k]; } };
|
||||
}
|
||||
Object.defineProperty(o, k2, desc);
|
||||
}) : (function(o, m, k, k2) {
|
||||
if (k2 === undefined) k2 = k;
|
||||
o[k2] = m[k];
|
||||
}));
|
||||
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
||||
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
||||
};
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.Storage = exports.IdempotencyStrategy = exports.Notification = exports.Iam = exports.HmacKey = exports.File = exports.Channel = exports.Bucket = void 0;
|
||||
var bucket_1 = require("./bucket");
|
||||
Object.defineProperty(exports, "Bucket", { enumerable: true, get: function () { return bucket_1.Bucket; } });
|
||||
__exportStar(require("./crc32c"), exports);
|
||||
var channel_1 = require("./channel");
|
||||
Object.defineProperty(exports, "Channel", { enumerable: true, get: function () { return channel_1.Channel; } });
|
||||
var file_1 = require("./file");
|
||||
Object.defineProperty(exports, "File", { enumerable: true, get: function () { return file_1.File; } });
|
||||
__exportStar(require("./hash-stream-validator"), exports);
|
||||
var hmacKey_1 = require("./hmacKey");
|
||||
Object.defineProperty(exports, "HmacKey", { enumerable: true, get: function () { return hmacKey_1.HmacKey; } });
|
||||
var iam_1 = require("./iam");
|
||||
Object.defineProperty(exports, "Iam", { enumerable: true, get: function () { return iam_1.Iam; } });
|
||||
var notification_1 = require("./notification");
|
||||
Object.defineProperty(exports, "Notification", { enumerable: true, get: function () { return notification_1.Notification; } });
|
||||
var storage_1 = require("./storage");
|
||||
Object.defineProperty(exports, "IdempotencyStrategy", { enumerable: true, get: function () { return storage_1.IdempotencyStrategy; } });
|
||||
Object.defineProperty(exports, "Storage", { enumerable: true, get: function () { return storage_1.Storage; } });
|
||||
__exportStar(require("./transfer-manager"), exports);
|
||||
//# sourceMappingURL=index.js.map
|
||||
@ -0,0 +1,19 @@
|
||||
/*!
|
||||
* Copyright 2022 Google LLC. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
export { GoogleAuthOptions } from 'google-auth-library';
|
||||
export { Service, ServiceConfig, ServiceOptions, StreamRequestOptions, } from './service';
|
||||
export { DeleteCallback, ExistsCallback, GetConfig, InstanceResponseCallback, Interceptor, Metadata, MetadataCallback, MetadataResponse, Methods, ResponseCallback, ServiceObject, ServiceObjectConfig, ServiceObjectParent, SetMetadataResponse, } from './service-object';
|
||||
export { Abortable, AbortableDuplex, ApiError, BodyResponseCallback, DecorateRequestOptions, ResponseBody, util, } from './util';
|
||||
@ -0,0 +1,11 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.util = exports.ApiError = exports.ServiceObject = exports.Service = void 0;
|
||||
var service_1 = require("./service");
|
||||
Object.defineProperty(exports, "Service", { enumerable: true, get: function () { return service_1.Service; } });
|
||||
var service_object_1 = require("./service-object");
|
||||
Object.defineProperty(exports, "ServiceObject", { enumerable: true, get: function () { return service_object_1.ServiceObject; } });
|
||||
var util_1 = require("./util");
|
||||
Object.defineProperty(exports, "ApiError", { enumerable: true, get: function () { return util_1.ApiError; } });
|
||||
Object.defineProperty(exports, "util", { enumerable: true, get: function () { return util_1.util; } });
|
||||
//# sourceMappingURL=index.js.map
|
||||
212
node_modules/@google-cloud/storage/build/src/nodejs-common/service-object.d.ts
generated
vendored
212
node_modules/@google-cloud/storage/build/src/nodejs-common/service-object.d.ts
generated
vendored
@ -0,0 +1,212 @@
|
||||
/// <reference types="node" />
|
||||
import { EventEmitter } from 'events';
|
||||
import * as r from 'teeny-request';
|
||||
import { ApiError, BodyResponseCallback, DecorateRequestOptions } from './util';
|
||||
export type RequestResponse = [Metadata, r.Response];
|
||||
export interface ServiceObjectParent {
|
||||
interceptors: Interceptor[];
|
||||
getRequestInterceptors(): Function[];
|
||||
requestStream(reqOpts: DecorateRequestOptions): r.Request;
|
||||
request(reqOpts: DecorateRequestOptions, callback: BodyResponseCallback): void;
|
||||
}
|
||||
export interface Interceptor {
|
||||
request(opts: r.Options): DecorateRequestOptions;
|
||||
}
|
||||
export type GetMetadataOptions = object;
|
||||
export type Metadata = any;
|
||||
export type MetadataResponse = [Metadata, r.Response];
|
||||
export type MetadataCallback = (err: Error | null, metadata?: Metadata, apiResponse?: r.Response) => void;
|
||||
export type ExistsOptions = object;
|
||||
export interface ExistsCallback {
|
||||
(err: Error | null, exists?: boolean): void;
|
||||
}
|
||||
export interface ServiceObjectConfig {
|
||||
/**
|
||||
* The base URL to make API requests to.
|
||||
*/
|
||||
baseUrl?: string;
|
||||
/**
|
||||
* The method which creates this object.
|
||||
*/
|
||||
createMethod?: Function;
|
||||
/**
|
||||
* The identifier of the object. For example, the name of a Storage bucket or
|
||||
* Pub/Sub topic.
|
||||
*/
|
||||
id?: string;
|
||||
/**
|
||||
* A map of each method name that should be inherited.
|
||||
*/
|
||||
methods?: Methods;
|
||||
/**
|
||||
* The parent service instance. For example, an instance of Storage if the
|
||||
* object is Bucket.
|
||||
*/
|
||||
parent: ServiceObjectParent;
|
||||
/**
|
||||
* Override of projectId, used to allow access to resources in another project.
|
||||
* For example, a BigQuery dataset in another project to which the user has been
|
||||
* granted permission.
|
||||
*/
|
||||
projectId?: string;
|
||||
}
|
||||
export interface Methods {
|
||||
[methodName: string]: {
|
||||
reqOpts?: r.CoreOptions;
|
||||
} | boolean;
|
||||
}
|
||||
export interface InstanceResponseCallback<T> {
|
||||
(err: ApiError | null, instance?: T | null, apiResponse?: r.Response): void;
|
||||
}
|
||||
export interface CreateOptions {
|
||||
}
|
||||
export type CreateResponse<T> = any[];
|
||||
export interface CreateCallback<T> {
|
||||
(err: ApiError | null, instance?: T | null, ...args: any[]): void;
|
||||
}
|
||||
export type DeleteOptions = {
|
||||
ignoreNotFound?: boolean;
|
||||
ifGenerationMatch?: number;
|
||||
ifGenerationNotMatch?: number;
|
||||
ifMetagenerationMatch?: number;
|
||||
ifMetagenerationNotMatch?: number;
|
||||
} & object;
|
||||
export interface DeleteCallback {
|
||||
(err: Error | null, apiResponse?: r.Response): void;
|
||||
}
|
||||
export interface GetConfig {
|
||||
/**
|
||||
* Create the object if it doesn't already exist.
|
||||
*/
|
||||
autoCreate?: boolean;
|
||||
}
|
||||
type GetOrCreateOptions = GetConfig & CreateOptions;
|
||||
export type GetResponse<T> = [T, r.Response];
|
||||
export interface ResponseCallback {
|
||||
(err?: Error | null, apiResponse?: r.Response): void;
|
||||
}
|
||||
export type SetMetadataResponse = [Metadata];
|
||||
export type SetMetadataOptions = object;
|
||||
/**
|
||||
* ServiceObject is a base class, meant to be inherited from by a "service
|
||||
* object," like a BigQuery dataset or Storage bucket.
|
||||
*
|
||||
* Most of the time, these objects share common functionality; they can be
|
||||
* created or deleted, and you can get or set their metadata.
|
||||
*
|
||||
* By inheriting from this class, a service object will be extended with these
|
||||
* shared behaviors. Note that any method can be overridden when the service
|
||||
* object requires specific behavior.
|
||||
*/
|
||||
declare class ServiceObject<T = any> extends EventEmitter {
|
||||
metadata: Metadata;
|
||||
baseUrl?: string;
|
||||
parent: ServiceObjectParent;
|
||||
id?: string;
|
||||
private createMethod?;
|
||||
protected methods: Methods;
|
||||
interceptors: Interceptor[];
|
||||
projectId?: string;
|
||||
constructor(config: ServiceObjectConfig);
|
||||
/**
|
||||
* Create the object.
|
||||
*
|
||||
* @param {object=} options - Configuration object.
|
||||
* @param {function} callback - The callback function.
|
||||
* @param {?error} callback.err - An error returned while making this request.
|
||||
* @param {object} callback.instance - The instance.
|
||||
* @param {object} callback.apiResponse - The full API response.
|
||||
*/
|
||||
create(options?: CreateOptions): Promise<CreateResponse<T>>;
|
||||
create(options: CreateOptions, callback: CreateCallback<T>): void;
|
||||
create(callback: CreateCallback<T>): void;
|
||||
/**
|
||||
* Delete the object.
|
||||
*
|
||||
* @param {function=} callback - The callback function.
|
||||
* @param {?error} callback.err - An error returned while making this request.
|
||||
* @param {object} callback.apiResponse - The full API response.
|
||||
*/
|
||||
delete(options?: DeleteOptions): Promise<[r.Response]>;
|
||||
delete(options: DeleteOptions, callback: DeleteCallback): void;
|
||||
delete(callback: DeleteCallback): void;
|
||||
/**
|
||||
* Check if the object exists.
|
||||
*
|
||||
* @param {function} callback - The callback function.
|
||||
* @param {?error} callback.err - An error returned while making this request.
|
||||
* @param {boolean} callback.exists - Whether the object exists or not.
|
||||
*/
|
||||
exists(options?: ExistsOptions): Promise<[boolean]>;
|
||||
exists(options: ExistsOptions, callback: ExistsCallback): void;
|
||||
exists(callback: ExistsCallback): void;
|
||||
/**
|
||||
* Get the object if it exists. Optionally have the object created if an
|
||||
* options object is provided with `autoCreate: true`.
|
||||
*
|
||||
* @param {object=} options - The configuration object that will be used to
|
||||
* create the object if necessary.
|
||||
* @param {boolean} options.autoCreate - Create the object if it doesn't already exist.
|
||||
* @param {function} callback - The callback function.
|
||||
* @param {?error} callback.err - An error returned while making this request.
|
||||
* @param {object} callback.instance - The instance.
|
||||
* @param {object} callback.apiResponse - The full API response.
|
||||
*/
|
||||
get(options?: GetOrCreateOptions): Promise<GetResponse<T>>;
|
||||
get(callback: InstanceResponseCallback<T>): void;
|
||||
get(options: GetOrCreateOptions, callback: InstanceResponseCallback<T>): void;
|
||||
/**
|
||||
* Get the metadata of this object.
|
||||
*
|
||||
* @param {function} callback - The callback function.
|
||||
* @param {?error} callback.err - An error returned while making this request.
|
||||
* @param {object} callback.metadata - The metadata for this object.
|
||||
* @param {object} callback.apiResponse - The full API response.
|
||||
*/
|
||||
getMetadata(options?: GetMetadataOptions): Promise<MetadataResponse>;
|
||||
getMetadata(options: GetMetadataOptions, callback: MetadataCallback): void;
|
||||
getMetadata(callback: MetadataCallback): void;
|
||||
/**
|
||||
* Return the user's custom request interceptors.
|
||||
*/
|
||||
getRequestInterceptors(): Function[];
|
||||
/**
|
||||
* Set the metadata for this object.
|
||||
*
|
||||
* @param {object} metadata - The metadata to set on this object.
|
||||
* @param {object=} options - Configuration options.
|
||||
* @param {function=} callback - The callback function.
|
||||
* @param {?error} callback.err - An error returned while making this request.
|
||||
* @param {object} callback.apiResponse - The full API response.
|
||||
*/
|
||||
setMetadata(metadata: Metadata, options?: SetMetadataOptions): Promise<SetMetadataResponse>;
|
||||
setMetadata(metadata: Metadata, callback: MetadataCallback): void;
|
||||
setMetadata(metadata: Metadata, options: SetMetadataOptions, callback: MetadataCallback): void;
|
||||
/**
|
||||
* Make an authenticated API request.
|
||||
*
|
||||
* @private
|
||||
*
|
||||
* @param {object} reqOpts - Request options that are passed to `request`.
|
||||
* @param {string} reqOpts.uri - A URI relative to the baseUrl.
|
||||
* @param {function} callback - The callback function passed to `request`.
|
||||
*/
|
||||
private request_;
|
||||
/**
|
||||
* Make an authenticated API request.
|
||||
*
|
||||
* @param {object} reqOpts - Request options that are passed to `request`.
|
||||
* @param {string} reqOpts.uri - A URI relative to the baseUrl.
|
||||
* @param {function} callback - The callback function passed to `request`.
|
||||
*/
|
||||
request(reqOpts: DecorateRequestOptions): Promise<RequestResponse>;
|
||||
request(reqOpts: DecorateRequestOptions, callback: BodyResponseCallback): void;
|
||||
/**
|
||||
* Make an authenticated API request.
|
||||
*
|
||||
* @param {object} reqOpts - Request options that are passed to `request`.
|
||||
* @param {string} reqOpts.uri - A URI relative to the baseUrl.
|
||||
*/
|
||||
requestStream(reqOpts: DecorateRequestOptions): r.Request;
|
||||
}
|
||||
export { ServiceObject };
|
||||
@ -0,0 +1,280 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.ServiceObject = void 0;
|
||||
/*!
|
||||
* Copyright 2022 Google LLC. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
const promisify_1 = require("@google-cloud/promisify");
|
||||
const events_1 = require("events");
|
||||
const extend = require("extend");
|
||||
const util_1 = require("./util");
|
||||
/**
|
||||
* ServiceObject is a base class, meant to be inherited from by a "service
|
||||
* object," like a BigQuery dataset or Storage bucket.
|
||||
*
|
||||
* Most of the time, these objects share common functionality; they can be
|
||||
* created or deleted, and you can get or set their metadata.
|
||||
*
|
||||
* By inheriting from this class, a service object will be extended with these
|
||||
* shared behaviors. Note that any method can be overridden when the service
|
||||
* object requires specific behavior.
|
||||
*/
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
class ServiceObject extends events_1.EventEmitter {
|
||||
/*
|
||||
* @constructor
|
||||
* @alias module:common/service-object
|
||||
*
|
||||
* @private
|
||||
*
|
||||
* @param {object} config - Configuration object.
|
||||
* @param {string} config.baseUrl - The base URL to make API requests to.
|
||||
* @param {string} config.createMethod - The method which creates this object.
|
||||
* @param {string=} config.id - The identifier of the object. For example, the
|
||||
* name of a Storage bucket or Pub/Sub topic.
|
||||
* @param {object=} config.methods - A map of each method name that should be inherited.
|
||||
* @param {object} config.methods[].reqOpts - Default request options for this
|
||||
* particular method. A common use case is when `setMetadata` requires a
|
||||
* `PUT` method to override the default `PATCH`.
|
||||
* @param {object} config.parent - The parent service instance. For example, an
|
||||
* instance of Storage if the object is Bucket.
|
||||
*/
|
||||
constructor(config) {
|
||||
super();
|
||||
this.metadata = {};
|
||||
this.baseUrl = config.baseUrl;
|
||||
this.parent = config.parent; // Parent class.
|
||||
this.id = config.id; // Name or ID (e.g. dataset ID, bucket name, etc).
|
||||
this.createMethod = config.createMethod;
|
||||
this.methods = config.methods || {};
|
||||
this.interceptors = [];
|
||||
this.projectId = config.projectId;
|
||||
if (config.methods) {
|
||||
// This filters the ServiceObject instance (e.g. a "File") to only have
|
||||
// the configured methods. We make a couple of exceptions for core-
|
||||
// functionality ("request()" and "getRequestInterceptors()")
|
||||
Object.getOwnPropertyNames(ServiceObject.prototype)
|
||||
.filter(methodName => {
|
||||
return (
|
||||
// All ServiceObjects need `request` and `getRequestInterceptors`.
|
||||
// clang-format off
|
||||
!/^request/.test(methodName) &&
|
||||
!/^getRequestInterceptors/.test(methodName) &&
|
||||
// clang-format on
|
||||
// The ServiceObject didn't redefine the method.
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
this[methodName] ===
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
ServiceObject.prototype[methodName] &&
|
||||
// This method isn't wanted.
|
||||
!config.methods[methodName]);
|
||||
})
|
||||
.forEach(methodName => {
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
this[methodName] = undefined;
|
||||
});
|
||||
}
|
||||
}
|
||||
create(optionsOrCallback, callback) {
|
||||
// eslint-disable-next-line @typescript-eslint/no-this-alias
|
||||
const self = this;
|
||||
const args = [this.id];
|
||||
if (typeof optionsOrCallback === 'function') {
|
||||
callback = optionsOrCallback;
|
||||
}
|
||||
if (typeof optionsOrCallback === 'object') {
|
||||
args.push(optionsOrCallback);
|
||||
}
|
||||
// Wrap the callback to return *this* instance of the object, not the
|
||||
// newly-created one.
|
||||
// tslint: disable-next-line no-any
|
||||
function onCreate(...args) {
|
||||
const [err, instance] = args;
|
||||
if (!err) {
|
||||
self.metadata = instance.metadata;
|
||||
if (self.id && instance.metadata) {
|
||||
self.id = instance.metadata.id;
|
||||
}
|
||||
args[1] = self; // replace the created `instance` with this one.
|
||||
}
|
||||
callback(...args);
|
||||
}
|
||||
args.push(onCreate);
|
||||
// eslint-disable-next-line prefer-spread
|
||||
this.createMethod.apply(null, args);
|
||||
}
|
||||
delete(optionsOrCallback, cb) {
|
||||
const [options, callback] = util_1.util.maybeOptionsOrCallback(optionsOrCallback, cb);
|
||||
const ignoreNotFound = options.ignoreNotFound;
|
||||
delete options.ignoreNotFound;
|
||||
const methodConfig = (typeof this.methods.delete === 'object' && this.methods.delete) || {};
|
||||
const reqOpts = extend(true, {
|
||||
method: 'DELETE',
|
||||
uri: '',
|
||||
}, methodConfig.reqOpts, {
|
||||
qs: options,
|
||||
});
|
||||
// The `request` method may have been overridden to hold any special
|
||||
// behavior. Ensure we call the original `request` method.
|
||||
ServiceObject.prototype.request.call(this, reqOpts, (err, ...args) => {
|
||||
if (err) {
|
||||
if (err.code === 404 && ignoreNotFound) {
|
||||
err = null;
|
||||
}
|
||||
}
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
callback(err, ...args);
|
||||
});
|
||||
}
|
||||
exists(optionsOrCallback, cb) {
|
||||
const [options, callback] = util_1.util.maybeOptionsOrCallback(optionsOrCallback, cb);
|
||||
this.get(options, err => {
|
||||
if (err) {
|
||||
if (err.code === 404) {
|
||||
callback(null, false);
|
||||
}
|
||||
else {
|
||||
callback(err);
|
||||
}
|
||||
return;
|
||||
}
|
||||
callback(null, true);
|
||||
});
|
||||
}
|
||||
get(optionsOrCallback, cb) {
|
||||
// eslint-disable-next-line @typescript-eslint/no-this-alias
|
||||
const self = this;
|
||||
const [opts, callback] = util_1.util.maybeOptionsOrCallback(optionsOrCallback, cb);
|
||||
const options = Object.assign({}, opts);
|
||||
const autoCreate = options.autoCreate && typeof this.create === 'function';
|
||||
delete options.autoCreate;
|
||||
function onCreate(err, instance, apiResponse) {
|
||||
if (err) {
|
||||
if (err.code === 409) {
|
||||
self.get(options, callback);
|
||||
return;
|
||||
}
|
||||
callback(err, null, apiResponse);
|
||||
return;
|
||||
}
|
||||
callback(null, instance, apiResponse);
|
||||
}
|
||||
this.getMetadata(options, (err, metadata) => {
|
||||
if (err) {
|
||||
if (err.code === 404 && autoCreate) {
|
||||
const args = [];
|
||||
if (Object.keys(options).length > 0) {
|
||||
args.push(options);
|
||||
}
|
||||
args.push(onCreate);
|
||||
self.create(...args);
|
||||
return;
|
||||
}
|
||||
callback(err, null, metadata);
|
||||
return;
|
||||
}
|
||||
callback(null, self, metadata);
|
||||
});
|
||||
}
|
||||
getMetadata(optionsOrCallback, cb) {
|
||||
const [options, callback] = util_1.util.maybeOptionsOrCallback(optionsOrCallback, cb);
|
||||
const methodConfig = (typeof this.methods.getMetadata === 'object' &&
|
||||
this.methods.getMetadata) ||
|
||||
{};
|
||||
const reqOpts = extend(true, {
|
||||
uri: '',
|
||||
}, methodConfig.reqOpts, {
|
||||
qs: options,
|
||||
});
|
||||
// The `request` method may have been overridden to hold any special
|
||||
// behavior. Ensure we call the original `request` method.
|
||||
ServiceObject.prototype.request.call(this, reqOpts, (err, body, res) => {
|
||||
this.metadata = body;
|
||||
callback(err, this.metadata, res);
|
||||
});
|
||||
}
|
||||
/**
|
||||
* Return the user's custom request interceptors.
|
||||
*/
|
||||
getRequestInterceptors() {
|
||||
// Interceptors should be returned in the order they were assigned.
|
||||
const localInterceptors = this.interceptors
|
||||
.filter(interceptor => typeof interceptor.request === 'function')
|
||||
.map(interceptor => interceptor.request);
|
||||
return this.parent.getRequestInterceptors().concat(localInterceptors);
|
||||
}
|
||||
setMetadata(metadata, optionsOrCallback, cb) {
|
||||
const [options, callback] = util_1.util.maybeOptionsOrCallback(optionsOrCallback, cb);
|
||||
const methodConfig = (typeof this.methods.setMetadata === 'object' &&
|
||||
this.methods.setMetadata) ||
|
||||
{};
|
||||
const reqOpts = extend(true, {}, {
|
||||
method: 'PATCH',
|
||||
uri: '',
|
||||
}, methodConfig.reqOpts, {
|
||||
json: metadata,
|
||||
qs: options,
|
||||
});
|
||||
// The `request` method may have been overridden to hold any special
|
||||
// behavior. Ensure we call the original `request` method.
|
||||
ServiceObject.prototype.request.call(this, reqOpts, (err, body, res) => {
|
||||
this.metadata = body;
|
||||
callback(err, this.metadata, res);
|
||||
});
|
||||
}
|
||||
request_(reqOpts, callback) {
|
||||
reqOpts = extend(true, {}, reqOpts);
|
||||
if (this.projectId) {
|
||||
reqOpts.projectId = this.projectId;
|
||||
}
|
||||
const isAbsoluteUrl = reqOpts.uri.indexOf('http') === 0;
|
||||
const uriComponents = [this.baseUrl, this.id || '', reqOpts.uri];
|
||||
if (isAbsoluteUrl) {
|
||||
uriComponents.splice(0, uriComponents.indexOf(reqOpts.uri));
|
||||
}
|
||||
reqOpts.uri = uriComponents
|
||||
.filter(x => x.trim()) // Limit to non-empty strings.
|
||||
.map(uriComponent => {
|
||||
const trimSlashesRegex = /^\/*|\/*$/g;
|
||||
return uriComponent.replace(trimSlashesRegex, '');
|
||||
})
|
||||
.join('/');
|
||||
const childInterceptors = Array.isArray(reqOpts.interceptors_)
|
||||
? reqOpts.interceptors_
|
||||
: [];
|
||||
const localInterceptors = [].slice.call(this.interceptors);
|
||||
reqOpts.interceptors_ = childInterceptors.concat(localInterceptors);
|
||||
if (reqOpts.shouldReturnStream) {
|
||||
return this.parent.requestStream(reqOpts);
|
||||
}
|
||||
this.parent.request(reqOpts, callback);
|
||||
}
|
||||
request(reqOpts, callback) {
|
||||
this.request_(reqOpts, callback);
|
||||
}
|
||||
/**
|
||||
* Make an authenticated API request.
|
||||
*
|
||||
* @param {object} reqOpts - Request options that are passed to `request`.
|
||||
* @param {string} reqOpts.uri - A URI relative to the baseUrl.
|
||||
*/
|
||||
requestStream(reqOpts) {
|
||||
const opts = extend(true, reqOpts, { shouldReturnStream: true });
|
||||
return this.request_(opts);
|
||||
}
|
||||
}
|
||||
exports.ServiceObject = ServiceObject;
|
||||
(0, promisify_1.promisifyAll)(ServiceObject, { exclude: ['getRequestInterceptors'] });
|
||||
//# sourceMappingURL=service-object.js.map
|
||||
@ -0,0 +1,105 @@
|
||||
import { AuthClient, GoogleAuth, GoogleAuthOptions } from 'google-auth-library';
|
||||
import * as r from 'teeny-request';
|
||||
import { Interceptor } from './service-object';
|
||||
import { BodyResponseCallback, DecorateRequestOptions, MakeAuthenticatedRequest, PackageJson } from './util';
|
||||
export declare const DEFAULT_PROJECT_ID_TOKEN = "{{projectId}}";
|
||||
export interface StreamRequestOptions extends DecorateRequestOptions {
|
||||
shouldReturnStream: true;
|
||||
}
|
||||
export interface ServiceConfig {
|
||||
/**
|
||||
* The base URL to make API requests to.
|
||||
*/
|
||||
baseUrl: string;
|
||||
/**
|
||||
* The API Endpoint to use when connecting to the service.
|
||||
* Example: storage.googleapis.com
|
||||
*/
|
||||
apiEndpoint: string;
|
||||
/**
|
||||
* The scopes required for the request.
|
||||
*/
|
||||
scopes: string[];
|
||||
projectIdRequired?: boolean;
|
||||
packageJson: PackageJson;
|
||||
/**
|
||||
* Reuse an existing `AuthClient` or `GoogleAuth` client instead of creating a new one.
|
||||
*/
|
||||
authClient?: AuthClient | GoogleAuth;
|
||||
}
|
||||
export interface ServiceOptions extends Omit<GoogleAuthOptions, 'authClient'> {
|
||||
authClient?: AuthClient | GoogleAuth;
|
||||
interceptors_?: Interceptor[];
|
||||
email?: string;
|
||||
token?: string;
|
||||
timeout?: number;
|
||||
userAgent?: string;
|
||||
useAuthWithCustomEndpoint?: boolean;
|
||||
}
|
||||
export declare class Service {
|
||||
baseUrl: string;
|
||||
private globalInterceptors;
|
||||
interceptors: Interceptor[];
|
||||
private packageJson;
|
||||
projectId: string;
|
||||
private projectIdRequired;
|
||||
providedUserAgent?: string;
|
||||
makeAuthenticatedRequest: MakeAuthenticatedRequest;
|
||||
authClient: GoogleAuth<AuthClient>;
|
||||
private getCredentials;
|
||||
readonly apiEndpoint: string;
|
||||
timeout?: number;
|
||||
/**
|
||||
* Service is a base class, meant to be inherited from by a "service," like
|
||||
* BigQuery or Storage.
|
||||
*
|
||||
* This handles making authenticated requests by exposing a `makeReq_`
|
||||
* function.
|
||||
*
|
||||
* @constructor
|
||||
* @alias module:common/service
|
||||
*
|
||||
* @param {object} config - Configuration object.
|
||||
* @param {string} config.baseUrl - The base URL to make API requests to.
|
||||
* @param {string[]} config.scopes - The scopes required for the request.
|
||||
* @param {object=} options - [Configuration object](#/docs).
|
||||
*/
|
||||
constructor(config: ServiceConfig, options?: ServiceOptions);
|
||||
/**
|
||||
* Return the user's custom request interceptors.
|
||||
*/
|
||||
getRequestInterceptors(): Function[];
|
||||
/**
|
||||
* Get and update the Service's project ID.
|
||||
*
|
||||
* @param {function} callback - The callback function.
|
||||
*/
|
||||
getProjectId(): Promise<string>;
|
||||
getProjectId(callback: (err: Error | null, projectId?: string) => void): void;
|
||||
protected getProjectIdAsync(): Promise<string>;
|
||||
/**
|
||||
* Make an authenticated API request.
|
||||
*
|
||||
* @private
|
||||
*
|
||||
* @param {object} reqOpts - Request options that are passed to `request`.
|
||||
* @param {string} reqOpts.uri - A URI relative to the baseUrl.
|
||||
* @param {function} callback - The callback function passed to `request`.
|
||||
*/
|
||||
private request_;
|
||||
/**
|
||||
* Make an authenticated API request.
|
||||
*
|
||||
* @param {object} reqOpts - Request options that are passed to `request`.
|
||||
* @param {string} reqOpts.uri - A URI relative to the baseUrl.
|
||||
* @param {function} callback - The callback function passed to `request`.
|
||||
*/
|
||||
request(reqOpts: DecorateRequestOptions, callback: BodyResponseCallback): void;
|
||||
/**
|
||||
* Make an authenticated API request.
|
||||
*
|
||||
* @param {object} reqOpts - Request options that are passed to `request`.
|
||||
* @param {string} reqOpts.uri - A URI relative to the baseUrl.
|
||||
*/
|
||||
requestStream(reqOpts: DecorateRequestOptions): r.Request;
|
||||
}
|
||||
@ -0,0 +1,177 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.Service = exports.DEFAULT_PROJECT_ID_TOKEN = void 0;
|
||||
/*!
|
||||
* Copyright 2022 Google LLC. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
const extend = require("extend");
|
||||
const uuid = require("uuid");
|
||||
const util_1 = require("./util");
|
||||
exports.DEFAULT_PROJECT_ID_TOKEN = '{{projectId}}';
|
||||
class Service {
|
||||
/**
|
||||
* Service is a base class, meant to be inherited from by a "service," like
|
||||
* BigQuery or Storage.
|
||||
*
|
||||
* This handles making authenticated requests by exposing a `makeReq_`
|
||||
* function.
|
||||
*
|
||||
* @constructor
|
||||
* @alias module:common/service
|
||||
*
|
||||
* @param {object} config - Configuration object.
|
||||
* @param {string} config.baseUrl - The base URL to make API requests to.
|
||||
* @param {string[]} config.scopes - The scopes required for the request.
|
||||
* @param {object=} options - [Configuration object](#/docs).
|
||||
*/
|
||||
constructor(config, options = {}) {
|
||||
this.baseUrl = config.baseUrl;
|
||||
this.apiEndpoint = config.apiEndpoint;
|
||||
this.timeout = options.timeout;
|
||||
this.globalInterceptors = Array.isArray(options.interceptors_)
|
||||
? options.interceptors_
|
||||
: [];
|
||||
this.interceptors = [];
|
||||
this.packageJson = config.packageJson;
|
||||
this.projectId = options.projectId || exports.DEFAULT_PROJECT_ID_TOKEN;
|
||||
this.projectIdRequired = config.projectIdRequired !== false;
|
||||
this.providedUserAgent = options.userAgent;
|
||||
const reqCfg = extend({}, config, {
|
||||
projectIdRequired: this.projectIdRequired,
|
||||
projectId: this.projectId,
|
||||
authClient: options.authClient,
|
||||
credentials: options.credentials,
|
||||
keyFile: options.keyFilename,
|
||||
email: options.email,
|
||||
token: options.token,
|
||||
});
|
||||
this.makeAuthenticatedRequest =
|
||||
util_1.util.makeAuthenticatedRequestFactory(reqCfg);
|
||||
this.authClient = this.makeAuthenticatedRequest.authClient;
|
||||
this.getCredentials = this.makeAuthenticatedRequest.getCredentials;
|
||||
const isCloudFunctionEnv = !!process.env.FUNCTION_NAME;
|
||||
if (isCloudFunctionEnv) {
|
||||
this.interceptors.push({
|
||||
request(reqOpts) {
|
||||
reqOpts.forever = false;
|
||||
return reqOpts;
|
||||
},
|
||||
});
|
||||
}
|
||||
}
|
||||
/**
|
||||
* Return the user's custom request interceptors.
|
||||
*/
|
||||
getRequestInterceptors() {
|
||||
// Interceptors should be returned in the order they were assigned.
|
||||
return [].slice
|
||||
.call(this.globalInterceptors)
|
||||
.concat(this.interceptors)
|
||||
.filter(interceptor => typeof interceptor.request === 'function')
|
||||
.map(interceptor => interceptor.request);
|
||||
}
|
||||
getProjectId(callback) {
|
||||
if (!callback) {
|
||||
return this.getProjectIdAsync();
|
||||
}
|
||||
this.getProjectIdAsync().then(p => callback(null, p), callback);
|
||||
}
|
||||
async getProjectIdAsync() {
|
||||
const projectId = await this.authClient.getProjectId();
|
||||
if (this.projectId === exports.DEFAULT_PROJECT_ID_TOKEN && projectId) {
|
||||
this.projectId = projectId;
|
||||
}
|
||||
return this.projectId;
|
||||
}
|
||||
request_(reqOpts, callback) {
|
||||
reqOpts = extend(true, {}, reqOpts, { timeout: this.timeout });
|
||||
const isAbsoluteUrl = reqOpts.uri.indexOf('http') === 0;
|
||||
const uriComponents = [this.baseUrl];
|
||||
if (this.projectIdRequired) {
|
||||
if (reqOpts.projectId) {
|
||||
uriComponents.push('projects');
|
||||
uriComponents.push(reqOpts.projectId);
|
||||
}
|
||||
else {
|
||||
uriComponents.push('projects');
|
||||
uriComponents.push(this.projectId);
|
||||
}
|
||||
}
|
||||
uriComponents.push(reqOpts.uri);
|
||||
if (isAbsoluteUrl) {
|
||||
uriComponents.splice(0, uriComponents.indexOf(reqOpts.uri));
|
||||
}
|
||||
reqOpts.uri = uriComponents
|
||||
.map(uriComponent => {
|
||||
const trimSlashesRegex = /^\/*|\/*$/g;
|
||||
return uriComponent.replace(trimSlashesRegex, '');
|
||||
})
|
||||
.join('/')
|
||||
// Some URIs have colon separators.
|
||||
// Bad: https://.../projects/:list
|
||||
// Good: https://.../projects:list
|
||||
.replace(/\/:/g, ':');
|
||||
const requestInterceptors = this.getRequestInterceptors();
|
||||
const interceptorArray = Array.isArray(reqOpts.interceptors_)
|
||||
? reqOpts.interceptors_
|
||||
: [];
|
||||
interceptorArray.forEach(interceptor => {
|
||||
if (typeof interceptor.request === 'function') {
|
||||
requestInterceptors.push(interceptor.request);
|
||||
}
|
||||
});
|
||||
requestInterceptors.forEach(requestInterceptor => {
|
||||
reqOpts = requestInterceptor(reqOpts);
|
||||
});
|
||||
delete reqOpts.interceptors_;
|
||||
const pkg = this.packageJson;
|
||||
let userAgent = util_1.util.getUserAgentFromPackageJson(pkg);
|
||||
if (this.providedUserAgent) {
|
||||
userAgent = `${this.providedUserAgent} ${userAgent}`;
|
||||
}
|
||||
reqOpts.headers = extend({}, reqOpts.headers, {
|
||||
'User-Agent': userAgent,
|
||||
'x-goog-api-client': `gl-node/${process.versions.node} gccl/${pkg.version} gccl-invocation-id/${uuid.v4()}`,
|
||||
});
|
||||
if (reqOpts.shouldReturnStream) {
|
||||
return this.makeAuthenticatedRequest(reqOpts);
|
||||
}
|
||||
else {
|
||||
this.makeAuthenticatedRequest(reqOpts, callback);
|
||||
}
|
||||
}
|
||||
/**
|
||||
* Make an authenticated API request.
|
||||
*
|
||||
* @param {object} reqOpts - Request options that are passed to `request`.
|
||||
* @param {string} reqOpts.uri - A URI relative to the baseUrl.
|
||||
* @param {function} callback - The callback function passed to `request`.
|
||||
*/
|
||||
request(reqOpts, callback) {
|
||||
Service.prototype.request_.call(this, reqOpts, callback);
|
||||
}
|
||||
/**
|
||||
* Make an authenticated API request.
|
||||
*
|
||||
* @param {object} reqOpts - Request options that are passed to `request`.
|
||||
* @param {string} reqOpts.uri - A URI relative to the baseUrl.
|
||||
*/
|
||||
requestStream(reqOpts) {
|
||||
const opts = extend(true, reqOpts, { shouldReturnStream: true });
|
||||
return Service.prototype.request_.call(this, opts);
|
||||
}
|
||||
}
|
||||
exports.Service = Service;
|
||||
//# sourceMappingURL=service.js.map
|
||||
@ -0,0 +1,331 @@
|
||||
/*!
|
||||
* Copyright 2022 Google LLC. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
/// <reference types="node" />
|
||||
import { AuthClient, GoogleAuth, GoogleAuthOptions } from 'google-auth-library';
|
||||
import { CredentialBody } from 'google-auth-library';
|
||||
import * as r from 'teeny-request';
|
||||
import { Duplex, DuplexOptions, Readable, Writable } from 'stream';
|
||||
import { Interceptor } from './service-object';
|
||||
export type ResponseBody = any;
|
||||
export interface DuplexifyOptions extends DuplexOptions {
|
||||
autoDestroy?: boolean;
|
||||
end?: boolean;
|
||||
}
|
||||
export interface Duplexify extends Duplex {
|
||||
readonly destroyed: boolean;
|
||||
setWritable(writable: Writable | false | null): void;
|
||||
setReadable(readable: Readable | false | null): void;
|
||||
}
|
||||
export interface DuplexifyConstructor {
|
||||
obj(writable?: Writable | false | null, readable?: Readable | false | null, options?: DuplexifyOptions): Duplexify;
|
||||
new (writable?: Writable | false | null, readable?: Readable | false | null, options?: DuplexifyOptions): Duplexify;
|
||||
(writable?: Writable | false | null, readable?: Readable | false | null, options?: DuplexifyOptions): Duplexify;
|
||||
}
|
||||
export interface ParsedHttpRespMessage {
|
||||
resp: r.Response;
|
||||
err?: ApiError;
|
||||
}
|
||||
export interface MakeAuthenticatedRequest {
|
||||
(reqOpts: DecorateRequestOptions): Duplexify;
|
||||
(reqOpts: DecorateRequestOptions, options?: MakeAuthenticatedRequestOptions): void | Abortable;
|
||||
(reqOpts: DecorateRequestOptions, callback?: BodyResponseCallback): void | Abortable;
|
||||
(reqOpts: DecorateRequestOptions, optionsOrCallback?: MakeAuthenticatedRequestOptions | BodyResponseCallback): void | Abortable | Duplexify;
|
||||
getCredentials: (callback: (err?: Error | null, credentials?: CredentialBody) => void) => void;
|
||||
authClient: GoogleAuth<AuthClient>;
|
||||
}
|
||||
export interface Abortable {
|
||||
abort(): void;
|
||||
}
|
||||
export type AbortableDuplex = Duplexify & Abortable;
|
||||
export interface PackageJson {
|
||||
name: string;
|
||||
version: string;
|
||||
}
|
||||
export interface MakeAuthenticatedRequestFactoryConfig extends Omit<GoogleAuthOptions, 'authClient'> {
|
||||
/**
|
||||
* Automatically retry requests if the response is related to rate limits or
|
||||
* certain intermittent server errors. We will exponentially backoff
|
||||
* subsequent requests by default. (default: true)
|
||||
*/
|
||||
autoRetry?: boolean;
|
||||
/**
|
||||
* If true, just return the provided request options. Default: false.
|
||||
*/
|
||||
customEndpoint?: boolean;
|
||||
/**
|
||||
* If true, will authenticate when using a custom endpoint. Default: false.
|
||||
*/
|
||||
useAuthWithCustomEndpoint?: boolean;
|
||||
/**
|
||||
* Account email address, required for PEM/P12 usage.
|
||||
*/
|
||||
email?: string;
|
||||
/**
|
||||
* Maximum number of automatic retries attempted before returning the error.
|
||||
* (default: 3)
|
||||
*/
|
||||
maxRetries?: number;
|
||||
stream?: Duplexify;
|
||||
/**
|
||||
* A pre-instantiated `AuthClient` or `GoogleAuth` client that should be used.
|
||||
* A new will be created if this is not set.
|
||||
*/
|
||||
authClient?: AuthClient | GoogleAuth;
|
||||
/**
|
||||
* Determines if a projectId is required for authenticated requests. Defaults to `true`.
|
||||
*/
|
||||
projectIdRequired?: boolean;
|
||||
}
|
||||
export interface MakeAuthenticatedRequestOptions {
|
||||
onAuthenticated: OnAuthenticatedCallback;
|
||||
}
|
||||
export interface OnAuthenticatedCallback {
|
||||
(err: Error | null, reqOpts?: DecorateRequestOptions): void;
|
||||
}
|
||||
export interface GoogleErrorBody {
|
||||
code: number;
|
||||
errors?: GoogleInnerError[];
|
||||
response: r.Response;
|
||||
message?: string;
|
||||
}
|
||||
export interface GoogleInnerError {
|
||||
reason?: string;
|
||||
message?: string;
|
||||
}
|
||||
export interface MakeWritableStreamOptions {
|
||||
/**
|
||||
* A connection instance used to get a token with and send the request
|
||||
* through.
|
||||
*/
|
||||
connection?: {};
|
||||
/**
|
||||
* Metadata to send at the head of the request.
|
||||
*/
|
||||
metadata?: {
|
||||
contentType?: string;
|
||||
};
|
||||
/**
|
||||
* Request object, in the format of a standard Node.js http.request() object.
|
||||
*/
|
||||
request?: r.Options;
|
||||
makeAuthenticatedRequest(reqOpts: r.OptionsWithUri, fnobj: {
|
||||
onAuthenticated(err: Error | null, authenticatedReqOpts?: r.Options): void;
|
||||
}): void;
|
||||
}
|
||||
export interface DecorateRequestOptions extends r.CoreOptions {
|
||||
autoPaginate?: boolean;
|
||||
autoPaginateVal?: boolean;
|
||||
objectMode?: boolean;
|
||||
maxRetries?: number;
|
||||
uri: string;
|
||||
interceptors_?: Interceptor[];
|
||||
shouldReturnStream?: boolean;
|
||||
projectId?: string;
|
||||
}
|
||||
export interface ParsedHttpResponseBody {
|
||||
body: ResponseBody;
|
||||
err?: Error;
|
||||
}
|
||||
/**
|
||||
* Custom error type for API errors.
|
||||
*
|
||||
* @param {object} errorBody - Error object.
|
||||
*/
|
||||
export declare class ApiError extends Error {
|
||||
code?: number;
|
||||
errors?: GoogleInnerError[];
|
||||
response?: r.Response;
|
||||
constructor(errorMessage: string);
|
||||
constructor(errorBody: GoogleErrorBody);
|
||||
/**
|
||||
* Pieces together an error message by combining all unique error messages
|
||||
* returned from a single GoogleError
|
||||
*
|
||||
* @private
|
||||
*
|
||||
* @param {GoogleErrorBody} err The original error.
|
||||
* @param {GoogleInnerError[]} [errors] Inner errors, if any.
|
||||
* @returns {string}
|
||||
*/
|
||||
static createMultiErrorMessage(err: GoogleErrorBody, errors?: GoogleInnerError[]): string;
|
||||
}
|
||||
/**
|
||||
* Custom error type for partial errors returned from the API.
|
||||
*
|
||||
* @param {object} b - Error object.
|
||||
*/
|
||||
export declare class PartialFailureError extends Error {
|
||||
errors?: GoogleInnerError[];
|
||||
response?: r.Response;
|
||||
constructor(b: GoogleErrorBody);
|
||||
}
|
||||
export interface BodyResponseCallback {
|
||||
(err: Error | ApiError | null, body?: ResponseBody, res?: r.Response): void;
|
||||
}
|
||||
export interface RetryOptions {
|
||||
retryDelayMultiplier?: number;
|
||||
totalTimeout?: number;
|
||||
maxRetryDelay?: number;
|
||||
autoRetry?: boolean;
|
||||
maxRetries?: number;
|
||||
retryableErrorFn?: (err: ApiError) => boolean;
|
||||
}
|
||||
export interface MakeRequestConfig {
|
||||
/**
|
||||
* Automatically retry requests if the response is related to rate limits or
|
||||
* certain intermittent server errors. We will exponentially backoff
|
||||
* subsequent requests by default. (default: true)
|
||||
*/
|
||||
autoRetry?: boolean;
|
||||
/**
|
||||
* Maximum number of automatic retries attempted before returning the error.
|
||||
* (default: 3)
|
||||
*/
|
||||
maxRetries?: number;
|
||||
retries?: number;
|
||||
retryOptions?: RetryOptions;
|
||||
stream?: Duplexify;
|
||||
shouldRetryFn?: (response?: r.Response) => boolean;
|
||||
}
|
||||
export declare class Util {
|
||||
ApiError: typeof ApiError;
|
||||
PartialFailureError: typeof PartialFailureError;
|
||||
/**
|
||||
* No op.
|
||||
*
|
||||
* @example
|
||||
* function doSomething(callback) {
|
||||
* callback = callback || noop;
|
||||
* }
|
||||
*/
|
||||
noop(): void;
|
||||
/**
|
||||
* Uniformly process an API response.
|
||||
*
|
||||
* @param {*} err - Error value.
|
||||
* @param {*} resp - Response value.
|
||||
* @param {*} body - Body value.
|
||||
* @param {function} callback - The callback function.
|
||||
*/
|
||||
handleResp(err: Error | null, resp?: r.Response | null, body?: ResponseBody, callback?: BodyResponseCallback): void;
|
||||
/**
|
||||
* Sniff an incoming HTTP response message for errors.
|
||||
*
|
||||
* @param {object} httpRespMessage - An incoming HTTP response message from `request`.
|
||||
* @return {object} parsedHttpRespMessage - The parsed response.
|
||||
* @param {?error} parsedHttpRespMessage.err - An error detected.
|
||||
* @param {object} parsedHttpRespMessage.resp - The original response object.
|
||||
*/
|
||||
parseHttpRespMessage(httpRespMessage: r.Response): ParsedHttpRespMessage;
|
||||
/**
|
||||
* Parse the response body from an HTTP request.
|
||||
*
|
||||
* @param {object} body - The response body.
|
||||
* @return {object} parsedHttpRespMessage - The parsed response.
|
||||
* @param {?error} parsedHttpRespMessage.err - An error detected.
|
||||
* @param {object} parsedHttpRespMessage.body - The original body value provided
|
||||
* will try to be JSON.parse'd. If it's successful, the parsed value will
|
||||
* be returned here, otherwise the original value and an error will be returned.
|
||||
*/
|
||||
parseHttpRespBody(body: ResponseBody): ParsedHttpResponseBody;
|
||||
/**
|
||||
* Take a Duplexify stream, fetch an authenticated connection header, and
|
||||
* create an outgoing writable stream.
|
||||
*
|
||||
* @param {Duplexify} dup - Duplexify stream.
|
||||
* @param {object} options - Configuration object.
|
||||
* @param {module:common/connection} options.connection - A connection instance used to get a token with and send the request through.
|
||||
* @param {object} options.metadata - Metadata to send at the head of the request.
|
||||
* @param {object} options.request - Request object, in the format of a standard Node.js http.request() object.
|
||||
* @param {string=} options.request.method - Default: "POST".
|
||||
* @param {string=} options.request.qs.uploadType - Default: "multipart".
|
||||
* @param {string=} options.streamContentType - Default: "application/octet-stream".
|
||||
* @param {function} onComplete - Callback, executed after the writable Request stream has completed.
|
||||
*/
|
||||
makeWritableStream(dup: Duplexify, options: MakeWritableStreamOptions, onComplete?: Function): void;
|
||||
/**
|
||||
* Returns true if the API request should be retried, given the error that was
|
||||
* given the first time the request was attempted. This is used for rate limit
|
||||
* related errors as well as intermittent server errors.
|
||||
*
|
||||
* @param {error} err - The API error to check if it is appropriate to retry.
|
||||
* @return {boolean} True if the API request should be retried, false otherwise.
|
||||
*/
|
||||
shouldRetryRequest(err?: ApiError): boolean;
|
||||
/**
|
||||
* Get a function for making authenticated requests.
|
||||
*
|
||||
* @param {object} config - Configuration object.
|
||||
* @param {boolean=} config.autoRetry - Automatically retry requests if the
|
||||
* response is related to rate limits or certain intermittent server
|
||||
* errors. We will exponentially backoff subsequent requests by default.
|
||||
* (default: true)
|
||||
* @param {object=} config.credentials - Credentials object.
|
||||
* @param {boolean=} config.customEndpoint - If true, just return the provided request options. Default: false.
|
||||
* @param {boolean=} config.useAuthWithCustomEndpoint - If true, will authenticate when using a custom endpoint. Default: false.
|
||||
* @param {string=} config.email - Account email address, required for PEM/P12 usage.
|
||||
* @param {number=} config.maxRetries - Maximum number of automatic retries attempted before returning the error. (default: 3)
|
||||
* @param {string=} config.keyFile - Path to a .json, .pem, or .p12 keyfile.
|
||||
* @param {array} config.scopes - Array of scopes required for the API.
|
||||
*/
|
||||
makeAuthenticatedRequestFactory(config: MakeAuthenticatedRequestFactoryConfig): MakeAuthenticatedRequest;
|
||||
/**
|
||||
* Make a request through the `retryRequest` module with built-in error
|
||||
* handling and exponential back off.
|
||||
*
|
||||
* @param {object} reqOpts - Request options in the format `request` expects.
|
||||
* @param {object=} config - Configuration object.
|
||||
* @param {boolean=} config.autoRetry - Automatically retry requests if the
|
||||
* response is related to rate limits or certain intermittent server
|
||||
* errors. We will exponentially backoff subsequent requests by default.
|
||||
* (default: true)
|
||||
* @param {number=} config.maxRetries - Maximum number of automatic retries
|
||||
* attempted before returning the error. (default: 3)
|
||||
* @param {object=} config.request - HTTP module for request calls.
|
||||
* @param {function} callback - The callback function.
|
||||
*/
|
||||
makeRequest(reqOpts: DecorateRequestOptions, config: MakeRequestConfig, callback: BodyResponseCallback): void | Abortable;
|
||||
/**
|
||||
* Decorate the options about to be made in a request.
|
||||
*
|
||||
* @param {object} reqOpts - The options to be passed to `request`.
|
||||
* @param {string} projectId - The project ID.
|
||||
* @return {object} reqOpts - The decorated reqOpts.
|
||||
*/
|
||||
decorateRequest(reqOpts: DecorateRequestOptions, projectId: string): DecorateRequestOptions;
|
||||
isCustomType(unknown: any, module: string): boolean;
|
||||
/**
|
||||
* Create a properly-formatted User-Agent string from a package.json file.
|
||||
*
|
||||
* @param {object} packageJson - A module's package.json file.
|
||||
* @return {string} userAgent - The formatted User-Agent string.
|
||||
*/
|
||||
getUserAgentFromPackageJson(packageJson: PackageJson): string;
|
||||
/**
|
||||
* Given two parameters, figure out if this is either:
|
||||
* - Just a callback function
|
||||
* - An options object, and then a callback function
|
||||
* @param optionsOrCallback An options object or callback.
|
||||
* @param cb A potentially undefined callback.
|
||||
*/
|
||||
maybeOptionsOrCallback<T = {}, C = (err?: Error) => void>(optionsOrCallback?: T | C, cb?: C): [T, C];
|
||||
_getDefaultHeaders(): {
|
||||
'User-Agent': string;
|
||||
'x-goog-api-client': string;
|
||||
};
|
||||
}
|
||||
declare const util: Util;
|
||||
export { util };
|
||||
@ -0,0 +1,664 @@
|
||||
"use strict";
|
||||
/*!
|
||||
* Copyright 2022 Google LLC. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.util = exports.Util = exports.PartialFailureError = exports.ApiError = void 0;
|
||||
/*!
|
||||
* @module common/util
|
||||
*/
|
||||
const projectify_1 = require("@google-cloud/projectify");
|
||||
const ent = require("ent");
|
||||
const extend = require("extend");
|
||||
const google_auth_library_1 = require("google-auth-library");
|
||||
const retryRequest = require("retry-request");
|
||||
const stream_1 = require("stream");
|
||||
const teeny_request_1 = require("teeny-request");
|
||||
const uuid = require("uuid");
|
||||
const service_1 = require("./service");
|
||||
const packageJson = require('../../../package.json');
|
||||
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
||||
const duplexify = require('duplexify');
|
||||
const requestDefaults = {
|
||||
timeout: 60000,
|
||||
gzip: true,
|
||||
forever: true,
|
||||
pool: {
|
||||
maxSockets: Infinity,
|
||||
},
|
||||
};
|
||||
/**
|
||||
* Default behavior: Automatically retry retriable server errors.
|
||||
*
|
||||
* @const {boolean}
|
||||
* @private
|
||||
*/
|
||||
const AUTO_RETRY_DEFAULT = true;
|
||||
/**
|
||||
* Default behavior: Only attempt to retry retriable errors 3 times.
|
||||
*
|
||||
* @const {number}
|
||||
* @private
|
||||
*/
|
||||
const MAX_RETRY_DEFAULT = 3;
|
||||
/**
|
||||
* Custom error type for API errors.
|
||||
*
|
||||
* @param {object} errorBody - Error object.
|
||||
*/
|
||||
class ApiError extends Error {
|
||||
constructor(errorBodyOrMessage) {
|
||||
super();
|
||||
if (typeof errorBodyOrMessage !== 'object') {
|
||||
this.message = errorBodyOrMessage || '';
|
||||
return;
|
||||
}
|
||||
const errorBody = errorBodyOrMessage;
|
||||
this.code = errorBody.code;
|
||||
this.errors = errorBody.errors;
|
||||
this.response = errorBody.response;
|
||||
try {
|
||||
this.errors = JSON.parse(this.response.body).error.errors;
|
||||
}
|
||||
catch (e) {
|
||||
this.errors = errorBody.errors;
|
||||
}
|
||||
this.message = ApiError.createMultiErrorMessage(errorBody, this.errors);
|
||||
Error.captureStackTrace(this);
|
||||
}
|
||||
/**
|
||||
* Pieces together an error message by combining all unique error messages
|
||||
* returned from a single GoogleError
|
||||
*
|
||||
* @private
|
||||
*
|
||||
* @param {GoogleErrorBody} err The original error.
|
||||
* @param {GoogleInnerError[]} [errors] Inner errors, if any.
|
||||
* @returns {string}
|
||||
*/
|
||||
static createMultiErrorMessage(err, errors) {
|
||||
const messages = new Set();
|
||||
if (err.message) {
|
||||
messages.add(err.message);
|
||||
}
|
||||
if (errors && errors.length) {
|
||||
errors.forEach(({ message }) => messages.add(message));
|
||||
}
|
||||
else if (err.response && err.response.body) {
|
||||
messages.add(ent.decode(err.response.body.toString()));
|
||||
}
|
||||
else if (!err.message) {
|
||||
messages.add('A failure occurred during this request.');
|
||||
}
|
||||
let messageArr = Array.from(messages);
|
||||
if (messageArr.length > 1) {
|
||||
messageArr = messageArr.map((message, i) => ` ${i + 1}. ${message}`);
|
||||
messageArr.unshift('Multiple errors occurred during the request. Please see the `errors` array for complete details.\n');
|
||||
messageArr.push('\n');
|
||||
}
|
||||
return messageArr.join('\n');
|
||||
}
|
||||
}
|
||||
exports.ApiError = ApiError;
|
||||
/**
|
||||
* Custom error type for partial errors returned from the API.
|
||||
*
|
||||
* @param {object} b - Error object.
|
||||
*/
|
||||
class PartialFailureError extends Error {
|
||||
constructor(b) {
|
||||
super();
|
||||
const errorObject = b;
|
||||
this.errors = errorObject.errors;
|
||||
this.name = 'PartialFailureError';
|
||||
this.response = errorObject.response;
|
||||
this.message = ApiError.createMultiErrorMessage(errorObject, this.errors);
|
||||
}
|
||||
}
|
||||
exports.PartialFailureError = PartialFailureError;
|
||||
class Util {
|
||||
constructor() {
|
||||
this.ApiError = ApiError;
|
||||
this.PartialFailureError = PartialFailureError;
|
||||
}
|
||||
/**
|
||||
* No op.
|
||||
*
|
||||
* @example
|
||||
* function doSomething(callback) {
|
||||
* callback = callback || noop;
|
||||
* }
|
||||
*/
|
||||
noop() { }
|
||||
/**
|
||||
* Uniformly process an API response.
|
||||
*
|
||||
* @param {*} err - Error value.
|
||||
* @param {*} resp - Response value.
|
||||
* @param {*} body - Body value.
|
||||
* @param {function} callback - The callback function.
|
||||
*/
|
||||
handleResp(err, resp, body, callback) {
|
||||
callback = callback || util.noop;
|
||||
const parsedResp = extend(true, { err: err || null }, resp && util.parseHttpRespMessage(resp), body && util.parseHttpRespBody(body));
|
||||
// Assign the parsed body to resp.body, even if { json: false } was passed
|
||||
// as a request option.
|
||||
// We assume that nobody uses the previously unparsed value of resp.body.
|
||||
if (!parsedResp.err && resp && typeof parsedResp.body === 'object') {
|
||||
parsedResp.resp.body = parsedResp.body;
|
||||
}
|
||||
if (parsedResp.err && resp) {
|
||||
parsedResp.err.response = resp;
|
||||
}
|
||||
callback(parsedResp.err, parsedResp.body, parsedResp.resp);
|
||||
}
|
||||
/**
|
||||
* Sniff an incoming HTTP response message for errors.
|
||||
*
|
||||
* @param {object} httpRespMessage - An incoming HTTP response message from `request`.
|
||||
* @return {object} parsedHttpRespMessage - The parsed response.
|
||||
* @param {?error} parsedHttpRespMessage.err - An error detected.
|
||||
* @param {object} parsedHttpRespMessage.resp - The original response object.
|
||||
*/
|
||||
parseHttpRespMessage(httpRespMessage) {
|
||||
const parsedHttpRespMessage = {
|
||||
resp: httpRespMessage,
|
||||
};
|
||||
if (httpRespMessage.statusCode < 200 || httpRespMessage.statusCode > 299) {
|
||||
// Unknown error. Format according to ApiError standard.
|
||||
parsedHttpRespMessage.err = new ApiError({
|
||||
errors: new Array(),
|
||||
code: httpRespMessage.statusCode,
|
||||
message: httpRespMessage.statusMessage,
|
||||
response: httpRespMessage,
|
||||
});
|
||||
}
|
||||
return parsedHttpRespMessage;
|
||||
}
|
||||
/**
|
||||
* Parse the response body from an HTTP request.
|
||||
*
|
||||
* @param {object} body - The response body.
|
||||
* @return {object} parsedHttpRespMessage - The parsed response.
|
||||
* @param {?error} parsedHttpRespMessage.err - An error detected.
|
||||
* @param {object} parsedHttpRespMessage.body - The original body value provided
|
||||
* will try to be JSON.parse'd. If it's successful, the parsed value will
|
||||
* be returned here, otherwise the original value and an error will be returned.
|
||||
*/
|
||||
parseHttpRespBody(body) {
|
||||
const parsedHttpRespBody = {
|
||||
body,
|
||||
};
|
||||
if (typeof body === 'string') {
|
||||
try {
|
||||
parsedHttpRespBody.body = JSON.parse(body);
|
||||
}
|
||||
catch (err) {
|
||||
parsedHttpRespBody.body = body;
|
||||
}
|
||||
}
|
||||
if (parsedHttpRespBody.body && parsedHttpRespBody.body.error) {
|
||||
// Error from JSON API.
|
||||
parsedHttpRespBody.err = new ApiError(parsedHttpRespBody.body.error);
|
||||
}
|
||||
return parsedHttpRespBody;
|
||||
}
|
||||
/**
|
||||
* Take a Duplexify stream, fetch an authenticated connection header, and
|
||||
* create an outgoing writable stream.
|
||||
*
|
||||
* @param {Duplexify} dup - Duplexify stream.
|
||||
* @param {object} options - Configuration object.
|
||||
* @param {module:common/connection} options.connection - A connection instance used to get a token with and send the request through.
|
||||
* @param {object} options.metadata - Metadata to send at the head of the request.
|
||||
* @param {object} options.request - Request object, in the format of a standard Node.js http.request() object.
|
||||
* @param {string=} options.request.method - Default: "POST".
|
||||
* @param {string=} options.request.qs.uploadType - Default: "multipart".
|
||||
* @param {string=} options.streamContentType - Default: "application/octet-stream".
|
||||
* @param {function} onComplete - Callback, executed after the writable Request stream has completed.
|
||||
*/
|
||||
makeWritableStream(dup, options, onComplete) {
|
||||
onComplete = onComplete || util.noop;
|
||||
const writeStream = new ProgressStream();
|
||||
writeStream.on('progress', evt => dup.emit('progress', evt));
|
||||
dup.setWritable(writeStream);
|
||||
const defaultReqOpts = {
|
||||
method: 'POST',
|
||||
qs: {
|
||||
uploadType: 'multipart',
|
||||
},
|
||||
timeout: 0,
|
||||
maxRetries: 0,
|
||||
};
|
||||
const metadata = options.metadata || {};
|
||||
const reqOpts = extend(true, defaultReqOpts, options.request, {
|
||||
multipart: [
|
||||
{
|
||||
'Content-Type': 'application/json',
|
||||
body: JSON.stringify(metadata),
|
||||
},
|
||||
{
|
||||
'Content-Type': metadata.contentType || 'application/octet-stream',
|
||||
body: writeStream,
|
||||
},
|
||||
],
|
||||
});
|
||||
options.makeAuthenticatedRequest(reqOpts, {
|
||||
onAuthenticated(err, authenticatedReqOpts) {
|
||||
if (err) {
|
||||
dup.destroy(err);
|
||||
return;
|
||||
}
|
||||
requestDefaults.headers = util._getDefaultHeaders();
|
||||
const request = teeny_request_1.teenyRequest.defaults(requestDefaults);
|
||||
request(authenticatedReqOpts, (err, resp, body) => {
|
||||
util.handleResp(err, resp, body, (err, data) => {
|
||||
if (err) {
|
||||
dup.destroy(err);
|
||||
return;
|
||||
}
|
||||
dup.emit('response', resp);
|
||||
onComplete(data);
|
||||
});
|
||||
});
|
||||
},
|
||||
});
|
||||
}
|
||||
/**
|
||||
* Returns true if the API request should be retried, given the error that was
|
||||
* given the first time the request was attempted. This is used for rate limit
|
||||
* related errors as well as intermittent server errors.
|
||||
*
|
||||
* @param {error} err - The API error to check if it is appropriate to retry.
|
||||
* @return {boolean} True if the API request should be retried, false otherwise.
|
||||
*/
|
||||
shouldRetryRequest(err) {
|
||||
if (err) {
|
||||
if ([408, 429, 500, 502, 503, 504].indexOf(err.code) !== -1) {
|
||||
return true;
|
||||
}
|
||||
if (err.errors) {
|
||||
for (const e of err.errors) {
|
||||
const reason = e.reason;
|
||||
if (reason === 'rateLimitExceeded') {
|
||||
return true;
|
||||
}
|
||||
if (reason === 'userRateLimitExceeded') {
|
||||
return true;
|
||||
}
|
||||
if (reason && reason.includes('EAI_AGAIN')) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
/**
|
||||
* Get a function for making authenticated requests.
|
||||
*
|
||||
* @param {object} config - Configuration object.
|
||||
* @param {boolean=} config.autoRetry - Automatically retry requests if the
|
||||
* response is related to rate limits or certain intermittent server
|
||||
* errors. We will exponentially backoff subsequent requests by default.
|
||||
* (default: true)
|
||||
* @param {object=} config.credentials - Credentials object.
|
||||
* @param {boolean=} config.customEndpoint - If true, just return the provided request options. Default: false.
|
||||
* @param {boolean=} config.useAuthWithCustomEndpoint - If true, will authenticate when using a custom endpoint. Default: false.
|
||||
* @param {string=} config.email - Account email address, required for PEM/P12 usage.
|
||||
* @param {number=} config.maxRetries - Maximum number of automatic retries attempted before returning the error. (default: 3)
|
||||
* @param {string=} config.keyFile - Path to a .json, .pem, or .p12 keyfile.
|
||||
* @param {array} config.scopes - Array of scopes required for the API.
|
||||
*/
|
||||
makeAuthenticatedRequestFactory(config) {
|
||||
const googleAutoAuthConfig = extend({}, config);
|
||||
if (googleAutoAuthConfig.projectId === service_1.DEFAULT_PROJECT_ID_TOKEN) {
|
||||
delete googleAutoAuthConfig.projectId;
|
||||
}
|
||||
let authClient;
|
||||
if (googleAutoAuthConfig.authClient instanceof google_auth_library_1.GoogleAuth) {
|
||||
// Use an existing `GoogleAuth`
|
||||
authClient = googleAutoAuthConfig.authClient;
|
||||
}
|
||||
else {
|
||||
// Pass an `AuthClient` to `GoogleAuth`, if available
|
||||
const config = {
|
||||
...googleAutoAuthConfig,
|
||||
authClient: googleAutoAuthConfig.authClient,
|
||||
};
|
||||
authClient = new google_auth_library_1.GoogleAuth(config);
|
||||
}
|
||||
function makeAuthenticatedRequest(reqOpts, optionsOrCallback) {
|
||||
let stream;
|
||||
let projectId;
|
||||
const reqConfig = extend({}, config);
|
||||
let activeRequest_;
|
||||
if (!optionsOrCallback) {
|
||||
stream = duplexify();
|
||||
reqConfig.stream = stream;
|
||||
}
|
||||
const options = typeof optionsOrCallback === 'object' ? optionsOrCallback : undefined;
|
||||
const callback = typeof optionsOrCallback === 'function' ? optionsOrCallback : undefined;
|
||||
async function setProjectId() {
|
||||
projectId = await authClient.getProjectId();
|
||||
}
|
||||
const onAuthenticated = async (err, authenticatedReqOpts) => {
|
||||
const authLibraryError = err;
|
||||
const autoAuthFailed = err &&
|
||||
typeof err.message === 'string' &&
|
||||
err.message.indexOf('Could not load the default credentials') > -1;
|
||||
if (autoAuthFailed) {
|
||||
// Even though authentication failed, the API might not actually
|
||||
// care.
|
||||
authenticatedReqOpts = reqOpts;
|
||||
}
|
||||
if (!err || autoAuthFailed) {
|
||||
try {
|
||||
// Try with existing `projectId` value
|
||||
authenticatedReqOpts = util.decorateRequest(authenticatedReqOpts, projectId);
|
||||
err = null;
|
||||
}
|
||||
catch (e) {
|
||||
if (e instanceof projectify_1.MissingProjectIdError) {
|
||||
// A `projectId` was required, but we don't have one.
|
||||
try {
|
||||
// Attempt to get the `projectId`
|
||||
await setProjectId();
|
||||
authenticatedReqOpts = util.decorateRequest(authenticatedReqOpts, projectId);
|
||||
err = null;
|
||||
}
|
||||
catch (e) {
|
||||
// Re-use the "Could not load the default credentials error" if
|
||||
// auto auth failed.
|
||||
err = err || e;
|
||||
}
|
||||
}
|
||||
else {
|
||||
// Some other error unrelated to missing `projectId`
|
||||
err = err || e;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (err) {
|
||||
if (stream) {
|
||||
stream.destroy(err);
|
||||
}
|
||||
else {
|
||||
const fn = options && options.onAuthenticated
|
||||
? options.onAuthenticated
|
||||
: callback;
|
||||
fn(err);
|
||||
}
|
||||
return;
|
||||
}
|
||||
if (options && options.onAuthenticated) {
|
||||
options.onAuthenticated(null, authenticatedReqOpts);
|
||||
}
|
||||
else {
|
||||
activeRequest_ = util.makeRequest(authenticatedReqOpts, reqConfig, (apiResponseError, ...params) => {
|
||||
if (apiResponseError &&
|
||||
apiResponseError.code === 401 &&
|
||||
authLibraryError) {
|
||||
// Re-use the "Could not load the default credentials error" if
|
||||
// the API request failed due to missing credentials.
|
||||
apiResponseError = authLibraryError;
|
||||
}
|
||||
callback(apiResponseError, ...params);
|
||||
});
|
||||
}
|
||||
};
|
||||
const prepareRequest = async () => {
|
||||
try {
|
||||
const getProjectId = async () => {
|
||||
if (config.projectId &&
|
||||
config.projectId !== service_1.DEFAULT_PROJECT_ID_TOKEN) {
|
||||
// The user provided a project ID. We don't need to check with the
|
||||
// auth client, it could be incorrect.
|
||||
return config.projectId;
|
||||
}
|
||||
if (config.projectIdRequired === false) {
|
||||
// A projectId is not required. Return the default.
|
||||
return service_1.DEFAULT_PROJECT_ID_TOKEN;
|
||||
}
|
||||
return setProjectId();
|
||||
};
|
||||
const authorizeRequest = async () => {
|
||||
if (reqConfig.customEndpoint &&
|
||||
!reqConfig.useAuthWithCustomEndpoint) {
|
||||
// Using a custom API override. Do not use `google-auth-library` for
|
||||
// authentication. (ex: connecting to a local Datastore server)
|
||||
return reqOpts;
|
||||
}
|
||||
else {
|
||||
return authClient.authorizeRequest(reqOpts);
|
||||
}
|
||||
};
|
||||
const [_projectId, authorizedReqOpts] = await Promise.all([
|
||||
getProjectId(),
|
||||
authorizeRequest(),
|
||||
]);
|
||||
if (_projectId) {
|
||||
projectId = _projectId;
|
||||
}
|
||||
return onAuthenticated(null, authorizedReqOpts);
|
||||
}
|
||||
catch (e) {
|
||||
return onAuthenticated(e);
|
||||
}
|
||||
};
|
||||
prepareRequest();
|
||||
if (stream) {
|
||||
return stream;
|
||||
}
|
||||
return {
|
||||
abort() {
|
||||
setImmediate(() => {
|
||||
if (activeRequest_) {
|
||||
activeRequest_.abort();
|
||||
activeRequest_ = null;
|
||||
}
|
||||
});
|
||||
},
|
||||
};
|
||||
}
|
||||
const mar = makeAuthenticatedRequest;
|
||||
mar.getCredentials = authClient.getCredentials.bind(authClient);
|
||||
mar.authClient = authClient;
|
||||
return mar;
|
||||
}
|
||||
/**
|
||||
* Make a request through the `retryRequest` module with built-in error
|
||||
* handling and exponential back off.
|
||||
*
|
||||
* @param {object} reqOpts - Request options in the format `request` expects.
|
||||
* @param {object=} config - Configuration object.
|
||||
* @param {boolean=} config.autoRetry - Automatically retry requests if the
|
||||
* response is related to rate limits or certain intermittent server
|
||||
* errors. We will exponentially backoff subsequent requests by default.
|
||||
* (default: true)
|
||||
* @param {number=} config.maxRetries - Maximum number of automatic retries
|
||||
* attempted before returning the error. (default: 3)
|
||||
* @param {object=} config.request - HTTP module for request calls.
|
||||
* @param {function} callback - The callback function.
|
||||
*/
|
||||
makeRequest(reqOpts, config, callback) {
|
||||
var _a, _b, _c, _d, _e;
|
||||
let autoRetryValue = AUTO_RETRY_DEFAULT;
|
||||
if (config.autoRetry !== undefined) {
|
||||
autoRetryValue = config.autoRetry;
|
||||
}
|
||||
else if (((_a = config.retryOptions) === null || _a === void 0 ? void 0 : _a.autoRetry) !== undefined) {
|
||||
autoRetryValue = config.retryOptions.autoRetry;
|
||||
}
|
||||
let maxRetryValue = MAX_RETRY_DEFAULT;
|
||||
if (config.maxRetries !== undefined) {
|
||||
maxRetryValue = config.maxRetries;
|
||||
}
|
||||
else if (((_b = config.retryOptions) === null || _b === void 0 ? void 0 : _b.maxRetries) !== undefined) {
|
||||
maxRetryValue = config.retryOptions.maxRetries;
|
||||
}
|
||||
requestDefaults.headers = this._getDefaultHeaders();
|
||||
const options = {
|
||||
request: teeny_request_1.teenyRequest.defaults(requestDefaults),
|
||||
retries: autoRetryValue !== false ? maxRetryValue : 0,
|
||||
noResponseRetries: autoRetryValue !== false ? maxRetryValue : 0,
|
||||
shouldRetryFn(httpRespMessage) {
|
||||
var _a, _b;
|
||||
const err = util.parseHttpRespMessage(httpRespMessage).err;
|
||||
if ((_a = config.retryOptions) === null || _a === void 0 ? void 0 : _a.retryableErrorFn) {
|
||||
return err && ((_b = config.retryOptions) === null || _b === void 0 ? void 0 : _b.retryableErrorFn(err));
|
||||
}
|
||||
return err && util.shouldRetryRequest(err);
|
||||
},
|
||||
maxRetryDelay: (_c = config.retryOptions) === null || _c === void 0 ? void 0 : _c.maxRetryDelay,
|
||||
retryDelayMultiplier: (_d = config.retryOptions) === null || _d === void 0 ? void 0 : _d.retryDelayMultiplier,
|
||||
totalTimeout: (_e = config.retryOptions) === null || _e === void 0 ? void 0 : _e.totalTimeout,
|
||||
};
|
||||
if (typeof reqOpts.maxRetries === 'number') {
|
||||
options.retries = reqOpts.maxRetries;
|
||||
options.noResponseRetries = reqOpts.maxRetries;
|
||||
}
|
||||
if (!config.stream) {
|
||||
return retryRequest(reqOpts, options,
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
(err, response, body) => {
|
||||
util.handleResp(err, response, body, callback);
|
||||
});
|
||||
}
|
||||
const dup = config.stream;
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
let requestStream;
|
||||
const isGetRequest = (reqOpts.method || 'GET').toUpperCase() === 'GET';
|
||||
if (isGetRequest) {
|
||||
requestStream = retryRequest(reqOpts, options);
|
||||
dup.setReadable(requestStream);
|
||||
}
|
||||
else {
|
||||
// Streaming writable HTTP requests cannot be retried.
|
||||
requestStream = options.request(reqOpts);
|
||||
dup.setWritable(requestStream);
|
||||
}
|
||||
// Replay the Request events back to the stream.
|
||||
requestStream
|
||||
.on('error', dup.destroy.bind(dup))
|
||||
.on('response', dup.emit.bind(dup, 'response'))
|
||||
.on('complete', dup.emit.bind(dup, 'complete'));
|
||||
dup.abort = requestStream.abort;
|
||||
return dup;
|
||||
}
|
||||
/**
|
||||
* Decorate the options about to be made in a request.
|
||||
*
|
||||
* @param {object} reqOpts - The options to be passed to `request`.
|
||||
* @param {string} projectId - The project ID.
|
||||
* @return {object} reqOpts - The decorated reqOpts.
|
||||
*/
|
||||
decorateRequest(reqOpts, projectId) {
|
||||
delete reqOpts.autoPaginate;
|
||||
delete reqOpts.autoPaginateVal;
|
||||
delete reqOpts.objectMode;
|
||||
if (reqOpts.qs !== null && typeof reqOpts.qs === 'object') {
|
||||
delete reqOpts.qs.autoPaginate;
|
||||
delete reqOpts.qs.autoPaginateVal;
|
||||
reqOpts.qs = (0, projectify_1.replaceProjectIdToken)(reqOpts.qs, projectId);
|
||||
}
|
||||
if (Array.isArray(reqOpts.multipart)) {
|
||||
reqOpts.multipart = reqOpts.multipart.map(part => {
|
||||
return (0, projectify_1.replaceProjectIdToken)(part, projectId);
|
||||
});
|
||||
}
|
||||
if (reqOpts.json !== null && typeof reqOpts.json === 'object') {
|
||||
delete reqOpts.json.autoPaginate;
|
||||
delete reqOpts.json.autoPaginateVal;
|
||||
reqOpts.json = (0, projectify_1.replaceProjectIdToken)(reqOpts.json, projectId);
|
||||
}
|
||||
reqOpts.uri = (0, projectify_1.replaceProjectIdToken)(reqOpts.uri, projectId);
|
||||
return reqOpts;
|
||||
}
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
isCustomType(unknown, module) {
|
||||
function getConstructorName(obj) {
|
||||
return obj.constructor && obj.constructor.name.toLowerCase();
|
||||
}
|
||||
const moduleNameParts = module.split('/');
|
||||
const parentModuleName = moduleNameParts[0] && moduleNameParts[0].toLowerCase();
|
||||
const subModuleName = moduleNameParts[1] && moduleNameParts[1].toLowerCase();
|
||||
if (subModuleName && getConstructorName(unknown) !== subModuleName) {
|
||||
return false;
|
||||
}
|
||||
let walkingModule = unknown;
|
||||
// eslint-disable-next-line no-constant-condition
|
||||
while (true) {
|
||||
if (getConstructorName(walkingModule) === parentModuleName) {
|
||||
return true;
|
||||
}
|
||||
walkingModule = walkingModule.parent;
|
||||
if (!walkingModule) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
/**
|
||||
* Create a properly-formatted User-Agent string from a package.json file.
|
||||
*
|
||||
* @param {object} packageJson - A module's package.json file.
|
||||
* @return {string} userAgent - The formatted User-Agent string.
|
||||
*/
|
||||
getUserAgentFromPackageJson(packageJson) {
|
||||
const hyphenatedPackageName = packageJson.name
|
||||
.replace('@google-cloud', 'gcloud-node') // For legacy purposes.
|
||||
.replace('/', '-'); // For UA spec-compliance purposes.
|
||||
return hyphenatedPackageName + '/' + packageJson.version;
|
||||
}
|
||||
/**
|
||||
* Given two parameters, figure out if this is either:
|
||||
* - Just a callback function
|
||||
* - An options object, and then a callback function
|
||||
* @param optionsOrCallback An options object or callback.
|
||||
* @param cb A potentially undefined callback.
|
||||
*/
|
||||
maybeOptionsOrCallback(optionsOrCallback, cb) {
|
||||
return typeof optionsOrCallback === 'function'
|
||||
? [{}, optionsOrCallback]
|
||||
: [optionsOrCallback, cb];
|
||||
}
|
||||
_getDefaultHeaders() {
|
||||
return {
|
||||
'User-Agent': util.getUserAgentFromPackageJson(packageJson),
|
||||
'x-goog-api-client': `gl-node/${process.versions.node} gccl/${packageJson.version} gccl-invocation-id/${uuid.v4()}`,
|
||||
};
|
||||
}
|
||||
}
|
||||
exports.Util = Util;
|
||||
/**
|
||||
* Basic Passthrough Stream that records the number of bytes read
|
||||
* every time the cursor is moved.
|
||||
*/
|
||||
class ProgressStream extends stream_1.Transform {
|
||||
constructor() {
|
||||
super(...arguments);
|
||||
this.bytesRead = 0;
|
||||
}
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
_transform(chunk, encoding, callback) {
|
||||
this.bytesRead += chunk.length;
|
||||
this.emit('progress', { bytesWritten: this.bytesRead, contentLength: '*' });
|
||||
this.push(chunk);
|
||||
callback();
|
||||
}
|
||||
}
|
||||
const util = new Util();
|
||||
exports.util = util;
|
||||
//# sourceMappingURL=util.js.map
|
||||
@ -0,0 +1,106 @@
|
||||
import { Metadata, MetadataCallback, ServiceObject } from './nodejs-common';
|
||||
import { ResponseBody } from './nodejs-common/util';
|
||||
import { Bucket } from './bucket';
|
||||
export interface DeleteNotificationOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export interface GetNotificationMetadataOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
/**
|
||||
* @typedef {array} GetNotificationMetadataResponse
|
||||
* @property {object} 0 The notification metadata.
|
||||
* @property {object} 1 The full API response.
|
||||
*/
|
||||
export type GetNotificationMetadataResponse = [ResponseBody, Metadata];
|
||||
/**
|
||||
* @callback GetNotificationMetadataCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {object} files The notification metadata.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
export interface GetNotificationMetadataCallback {
|
||||
(err: Error | null, metadata?: ResponseBody, apiResponse?: Metadata): void;
|
||||
}
|
||||
/**
|
||||
* @typedef {array} GetNotificationResponse
|
||||
* @property {Notification} 0 The {@link Notification}
|
||||
* @property {object} 1 The full API response.
|
||||
*/
|
||||
export type GetNotificationResponse = [Notification, Metadata];
|
||||
export interface GetNotificationOptions {
|
||||
/**
|
||||
* Automatically create the object if it does not exist. Default: `false`.
|
||||
*/
|
||||
autoCreate?: boolean;
|
||||
/**
|
||||
* The ID of the project which will be billed for the request.
|
||||
*/
|
||||
userProject?: string;
|
||||
}
|
||||
/**
|
||||
* @callback GetNotificationCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {Notification} notification The {@link Notification}.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
export interface GetNotificationCallback {
|
||||
(err: Error | null, notification?: Notification | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
/**
|
||||
* @callback DeleteNotificationCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
export interface DeleteNotificationCallback {
|
||||
(err: Error | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
/**
|
||||
* The API-formatted resource description of the notification.
|
||||
*
|
||||
* Note: This is not guaranteed to be up-to-date when accessed. To get the
|
||||
* latest record, call the `getMetadata()` method.
|
||||
*
|
||||
* @name Notification#metadata
|
||||
* @type {object}
|
||||
*/
|
||||
/**
|
||||
* A Notification object is created from your {@link Bucket} object using
|
||||
* {@link Bucket#notification}. Use it to interact with Cloud Pub/Sub
|
||||
* notifications.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/pubsub-notifications| Cloud Pub/Sub Notifications for Google Cloud Storage}
|
||||
*
|
||||
* @class
|
||||
* @hideconstructor
|
||||
*
|
||||
* @param {Bucket} bucket The bucket instance this notification is attached to.
|
||||
* @param {string} id The ID of the notification.
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
*
|
||||
* const notification = myBucket.notification('1');
|
||||
* ```
|
||||
*/
|
||||
declare class Notification extends ServiceObject {
|
||||
constructor(bucket: Bucket, id: string);
|
||||
delete(options?: DeleteNotificationOptions): Promise<[Metadata]>;
|
||||
delete(options: DeleteNotificationOptions, callback: DeleteNotificationCallback): void;
|
||||
delete(callback: DeleteNotificationCallback): void;
|
||||
get(options?: GetNotificationOptions): Promise<GetNotificationResponse>;
|
||||
get(options: GetNotificationOptions, callback: GetNotificationCallback): void;
|
||||
get(callback: GetNotificationCallback): void;
|
||||
getMetadata(options?: GetNotificationMetadataOptions): Promise<GetNotificationMetadataResponse>;
|
||||
getMetadata(options: GetNotificationMetadataOptions, callback: MetadataCallback): void;
|
||||
getMetadata(callback: MetadataCallback): void;
|
||||
}
|
||||
/**
|
||||
* Reference to the {@link Notification} class.
|
||||
* @name module:@google-cloud/storage.Notification
|
||||
* @see Notification
|
||||
*/
|
||||
export { Notification };
|
||||
@ -0,0 +1,311 @@
|
||||
"use strict";
|
||||
// Copyright 2019 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.Notification = void 0;
|
||||
const nodejs_common_1 = require("./nodejs-common");
|
||||
const promisify_1 = require("@google-cloud/promisify");
|
||||
/**
|
||||
* The API-formatted resource description of the notification.
|
||||
*
|
||||
* Note: This is not guaranteed to be up-to-date when accessed. To get the
|
||||
* latest record, call the `getMetadata()` method.
|
||||
*
|
||||
* @name Notification#metadata
|
||||
* @type {object}
|
||||
*/
|
||||
/**
|
||||
* A Notification object is created from your {@link Bucket} object using
|
||||
* {@link Bucket#notification}. Use it to interact with Cloud Pub/Sub
|
||||
* notifications.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/pubsub-notifications| Cloud Pub/Sub Notifications for Google Cloud Storage}
|
||||
*
|
||||
* @class
|
||||
* @hideconstructor
|
||||
*
|
||||
* @param {Bucket} bucket The bucket instance this notification is attached to.
|
||||
* @param {string} id The ID of the notification.
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
*
|
||||
* const notification = myBucket.notification('1');
|
||||
* ```
|
||||
*/
|
||||
class Notification extends nodejs_common_1.ServiceObject {
|
||||
constructor(bucket, id) {
|
||||
const methods = {
|
||||
/**
|
||||
* Creates a notification subscription for the bucket.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/notifications/insert| Notifications: insert}
|
||||
* @method Notification#create
|
||||
*
|
||||
* @param {Topic|string} topic The Cloud PubSub topic to which this
|
||||
* subscription publishes. If the project ID is omitted, the current
|
||||
* project ID will be used.
|
||||
*
|
||||
* Acceptable formats are:
|
||||
* - `projects/grape-spaceship-123/topics/my-topic`
|
||||
*
|
||||
* - `my-topic`
|
||||
* @param {CreateNotificationRequest} [options] Metadata to set for
|
||||
* the notification.
|
||||
* @param {CreateNotificationCallback} [callback] Callback function.
|
||||
* @returns {Promise<CreateNotificationResponse>}
|
||||
* @throws {Error} If a valid topic is not provided.
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
* const notification = myBucket.notification('1');
|
||||
*
|
||||
* notification.create(function(err, notification, apiResponse) {
|
||||
* if (!err) {
|
||||
* // The notification was created successfully.
|
||||
* }
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* notification.create().then(function(data) {
|
||||
* const notification = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
create: true,
|
||||
/**
|
||||
* @typedef {array} NotificationExistsResponse
|
||||
* @property {boolean} 0 Whether the notification exists or not.
|
||||
*/
|
||||
/**
|
||||
* @callback NotificationExistsCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {boolean} exists Whether the notification exists or not.
|
||||
*/
|
||||
/**
|
||||
* Check if the notification exists.
|
||||
*
|
||||
* @method Notification#exists
|
||||
* @param {NotificationExistsCallback} [callback] Callback function.
|
||||
* @returns {Promise<NotificationExistsResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
* const notification = myBucket.notification('1');
|
||||
*
|
||||
* notification.exists(function(err, exists) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* notification.exists().then(function(data) {
|
||||
* const exists = data[0];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
exists: true,
|
||||
};
|
||||
super({
|
||||
parent: bucket,
|
||||
baseUrl: '/notificationConfigs',
|
||||
id: id.toString(),
|
||||
createMethod: bucket.createNotification.bind(bucket),
|
||||
methods,
|
||||
});
|
||||
}
|
||||
/**
|
||||
* @typedef {array} DeleteNotificationResponse
|
||||
* @property {object} 0 The full API response.
|
||||
*/
|
||||
/**
|
||||
* Permanently deletes a notification subscription.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/notifications/delete| Notifications: delete API Documentation}
|
||||
*
|
||||
* @param {object} [options] Configuration options.
|
||||
* @param {string} [options.userProject] The ID of the project which will be
|
||||
* billed for the request.
|
||||
* @param {DeleteNotificationCallback} [callback] Callback function.
|
||||
* @returns {Promise<DeleteNotificationResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
* const notification = myBucket.notification('1');
|
||||
*
|
||||
* notification.delete(function(err, apiResponse) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* notification.delete().then(function(data) {
|
||||
* const apiResponse = data[0];
|
||||
* });
|
||||
*
|
||||
* ```
|
||||
* @example <caption>include:samples/deleteNotification.js</caption>
|
||||
* region_tag:storage_delete_bucket_notification
|
||||
* Another example:
|
||||
*/
|
||||
delete(optionsOrCallback, callback) {
|
||||
const options = typeof optionsOrCallback === 'object' ? optionsOrCallback : {};
|
||||
callback =
|
||||
typeof optionsOrCallback === 'function' ? optionsOrCallback : callback;
|
||||
this.request({
|
||||
method: 'DELETE',
|
||||
uri: '',
|
||||
qs: options,
|
||||
}, callback || nodejs_common_1.util.noop);
|
||||
}
|
||||
/**
|
||||
* Get a notification and its metadata if it exists.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/notifications/get| Notifications: get API Documentation}
|
||||
*
|
||||
* @param {object} [options] Configuration options.
|
||||
* See {@link Bucket#createNotification} for create options.
|
||||
* @param {boolean} [options.autoCreate] Automatically create the object if
|
||||
* it does not exist. Default: `false`.
|
||||
* @param {string} [options.userProject] The ID of the project which will be
|
||||
* billed for the request.
|
||||
* @param {GetNotificationCallback} [callback] Callback function.
|
||||
* @return {Promise<GetNotificationCallback>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
* const notification = myBucket.notification('1');
|
||||
*
|
||||
* notification.get(function(err, notification, apiResponse) {
|
||||
* // `notification.metadata` has been populated.
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* notification.get().then(function(data) {
|
||||
* const notification = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
get(optionsOrCallback, callback) {
|
||||
const options = typeof optionsOrCallback === 'object' ? optionsOrCallback : {};
|
||||
callback =
|
||||
typeof optionsOrCallback === 'function' ? optionsOrCallback : callback;
|
||||
const autoCreate = options.autoCreate;
|
||||
delete options.autoCreate;
|
||||
const onCreate = (err, notification, apiResponse) => {
|
||||
if (err) {
|
||||
if (err.code === 409) {
|
||||
this.get(options, callback);
|
||||
return;
|
||||
}
|
||||
callback(err, null, apiResponse);
|
||||
return;
|
||||
}
|
||||
callback(null, notification, apiResponse);
|
||||
};
|
||||
this.getMetadata(options, (err, metadata) => {
|
||||
if (err) {
|
||||
if (err.code === 404 && autoCreate) {
|
||||
const args = [];
|
||||
if (Object.keys(options).length > 0) {
|
||||
args.push(options);
|
||||
}
|
||||
args.push(onCreate);
|
||||
// eslint-disable-next-line
|
||||
this.create.apply(this, args);
|
||||
return;
|
||||
}
|
||||
callback(err, null, metadata);
|
||||
return;
|
||||
}
|
||||
callback(null, this, metadata);
|
||||
});
|
||||
}
|
||||
/**
|
||||
* Get the notification's metadata.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/json_api/v1/notifications/get| Notifications: get API Documentation}
|
||||
*
|
||||
* @param {object} [options] Configuration options.
|
||||
* @param {string} [options.userProject] The ID of the project which will be
|
||||
* billed for the request.
|
||||
* @param {GetNotificationMetadataCallback} [callback] Callback function.
|
||||
* @returns {Promise<GetNotificationMetadataResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const myBucket = storage.bucket('my-bucket');
|
||||
* const notification = myBucket.notification('1');
|
||||
*
|
||||
* notification.getMetadata(function(err, metadata, apiResponse) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* notification.getMetadata().then(function(data) {
|
||||
* const metadata = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
*
|
||||
* ```
|
||||
* @example <caption>include:samples/getMetadataNotifications.js</caption>
|
||||
* region_tag:storage_print_pubsub_bucket_notification
|
||||
* Another example:
|
||||
*/
|
||||
getMetadata(optionsOrCallback, callback) {
|
||||
const options = typeof optionsOrCallback === 'object' ? optionsOrCallback : {};
|
||||
callback =
|
||||
typeof optionsOrCallback === 'function' ? optionsOrCallback : callback;
|
||||
this.request({
|
||||
uri: '',
|
||||
qs: options,
|
||||
}, (err, resp) => {
|
||||
if (err) {
|
||||
callback(err, null, resp);
|
||||
return;
|
||||
}
|
||||
this.metadata = resp;
|
||||
callback(null, this.metadata, resp);
|
||||
});
|
||||
}
|
||||
}
|
||||
exports.Notification = Notification;
|
||||
/*! Developer Documentation
|
||||
*
|
||||
* All async methods (except for streams) will return a Promise in the event
|
||||
* that a callback is omitted.
|
||||
*/
|
||||
(0, promisify_1.promisifyAll)(Notification);
|
||||
//# sourceMappingURL=notification.js.map
|
||||
@ -0,0 +1,273 @@
|
||||
/// <reference types="node" />
|
||||
/// <reference types="node" />
|
||||
import { GaxiosOptions, GaxiosPromise, GaxiosResponse } from 'gaxios';
|
||||
import { GoogleAuthOptions } from 'google-auth-library';
|
||||
import { Writable, WritableOptions } from 'stream';
|
||||
import { RetryOptions, PreconditionOptions } from './storage';
|
||||
export declare const PROTOCOL_REGEX: RegExp;
|
||||
export interface ErrorWithCode extends Error {
|
||||
code: number;
|
||||
}
|
||||
export type CreateUriCallback = (err: Error | null, uri?: string) => void;
|
||||
export interface Encryption {
|
||||
key: {};
|
||||
hash: {};
|
||||
}
|
||||
export type PredefinedAcl = 'authenticatedRead' | 'bucketOwnerFullControl' | 'bucketOwnerRead' | 'private' | 'projectPrivate' | 'publicRead';
|
||||
export interface QueryParameters extends PreconditionOptions {
|
||||
contentEncoding?: string;
|
||||
kmsKeyName?: string;
|
||||
predefinedAcl?: PredefinedAcl;
|
||||
projection?: 'full' | 'noAcl';
|
||||
userProject?: string;
|
||||
}
|
||||
export interface UploadConfig extends Pick<WritableOptions, 'highWaterMark'> {
|
||||
/**
|
||||
* The API endpoint used for the request.
|
||||
* Defaults to `storage.googleapis.com`.
|
||||
* **Warning**:
|
||||
* If this value does not match the pattern *.googleapis.com,
|
||||
* an emulator context will be assumed and authentication will be bypassed.
|
||||
*/
|
||||
apiEndpoint?: string;
|
||||
/**
|
||||
* The name of the destination bucket.
|
||||
*/
|
||||
bucket: string;
|
||||
/**
|
||||
* The name of the destination file.
|
||||
*/
|
||||
file: string;
|
||||
/**
|
||||
* The GoogleAuthOptions passed to google-auth-library
|
||||
*/
|
||||
authConfig?: GoogleAuthOptions;
|
||||
/**
|
||||
* If you want to re-use an auth client from google-auto-auth, pass an
|
||||
* instance here.
|
||||
* Defaults to GoogleAuth and gets automatically overridden if an
|
||||
* emulator context is detected.
|
||||
*/
|
||||
authClient?: {
|
||||
request: <T>(opts: GaxiosOptions) => Promise<GaxiosResponse<T>> | GaxiosPromise<T>;
|
||||
};
|
||||
/**
|
||||
* Create a separate request per chunk.
|
||||
*
|
||||
* This value is in bytes and should be a multiple of 256 KiB (2^18).
|
||||
* We recommend using at least 8 MiB for the chunk size.
|
||||
*
|
||||
* @link https://cloud.google.com/storage/docs/performing-resumable-uploads#chunked-upload
|
||||
*/
|
||||
chunkSize?: number;
|
||||
/**
|
||||
* For each API request we send, you may specify custom request options that
|
||||
* we'll add onto the request. The request options follow the gaxios API:
|
||||
* https://github.com/googleapis/gaxios#request-options.
|
||||
*/
|
||||
customRequestOptions?: GaxiosOptions;
|
||||
/**
|
||||
* This will cause the upload to fail if the current generation of the remote
|
||||
* object does not match the one provided here.
|
||||
*/
|
||||
generation?: number;
|
||||
/**
|
||||
* A customer-supplied encryption key. See
|
||||
* https://cloud.google.com/storage/docs/encryption#customer-supplied.
|
||||
*/
|
||||
key?: string | Buffer;
|
||||
/**
|
||||
* Resource name of the Cloud KMS key, of the form
|
||||
* `projects/my-project/locations/global/keyRings/my-kr/cryptoKeys/my-key`,
|
||||
* that will be used to encrypt the object. Overrides the object metadata's
|
||||
* `kms_key_name` value, if any.
|
||||
*/
|
||||
kmsKeyName?: string;
|
||||
/**
|
||||
* Any metadata you wish to set on the object.
|
||||
*/
|
||||
metadata?: ConfigMetadata;
|
||||
/**
|
||||
* The starting byte of the upload stream, for resuming an interrupted upload.
|
||||
* See
|
||||
* https://cloud.google.com/storage/docs/json_api/v1/how-tos/resumable-upload#resume-upload.
|
||||
*/
|
||||
offset?: number;
|
||||
/**
|
||||
* Set an Origin header when creating the resumable upload URI.
|
||||
*/
|
||||
origin?: string;
|
||||
/**
|
||||
* Specify query parameters that go along with the initial upload request. See
|
||||
* https://cloud.google.com/storage/docs/json_api/v1/objects/insert#parameters
|
||||
*/
|
||||
params?: QueryParameters;
|
||||
/**
|
||||
* Apply a predefined set of access controls to the created file.
|
||||
*/
|
||||
predefinedAcl?: PredefinedAcl;
|
||||
/**
|
||||
* Make the uploaded file private. (Alias for config.predefinedAcl =
|
||||
* 'private')
|
||||
*/
|
||||
private?: boolean;
|
||||
/**
|
||||
* Make the uploaded file public. (Alias for config.predefinedAcl =
|
||||
* 'publicRead')
|
||||
*/
|
||||
public?: boolean;
|
||||
/**
|
||||
* If you already have a resumable URI from a previously-created resumable
|
||||
* upload, just pass it in here and we'll use that.
|
||||
*/
|
||||
uri?: string;
|
||||
/**
|
||||
* If the bucket being accessed has requesterPays functionality enabled, this
|
||||
* can be set to control which project is billed for the access of this file.
|
||||
*/
|
||||
userProject?: string;
|
||||
/**
|
||||
* Configuration options for retrying retryable errors.
|
||||
*/
|
||||
retryOptions: RetryOptions;
|
||||
}
|
||||
export interface ConfigMetadata {
|
||||
[key: string]: any;
|
||||
/**
|
||||
* Set the length of the file being uploaded.
|
||||
*/
|
||||
contentLength?: number;
|
||||
/**
|
||||
* Set the content type of the incoming data.
|
||||
*/
|
||||
contentType?: string;
|
||||
}
|
||||
export interface GoogleInnerError {
|
||||
reason?: string;
|
||||
}
|
||||
export interface ApiError extends Error {
|
||||
code?: number;
|
||||
errors?: GoogleInnerError[];
|
||||
}
|
||||
export declare class Upload extends Writable {
|
||||
#private;
|
||||
bucket: string;
|
||||
file: string;
|
||||
apiEndpoint: string;
|
||||
baseURI: string;
|
||||
authConfig?: {
|
||||
scopes?: string[];
|
||||
};
|
||||
authClient: {
|
||||
request: <T>(opts: GaxiosOptions) => Promise<GaxiosResponse<T>> | GaxiosPromise<T>;
|
||||
};
|
||||
cacheKey: string;
|
||||
chunkSize?: number;
|
||||
customRequestOptions: GaxiosOptions;
|
||||
generation?: number;
|
||||
key?: string | Buffer;
|
||||
kmsKeyName?: string;
|
||||
metadata: ConfigMetadata;
|
||||
offset?: number;
|
||||
origin?: string;
|
||||
params: QueryParameters;
|
||||
predefinedAcl?: PredefinedAcl;
|
||||
private?: boolean;
|
||||
public?: boolean;
|
||||
uri?: string;
|
||||
userProject?: string;
|
||||
encryption?: Encryption;
|
||||
uriProvidedManually: boolean;
|
||||
numBytesWritten: number;
|
||||
numRetries: number;
|
||||
contentLength: number | '*';
|
||||
retryOptions: RetryOptions;
|
||||
timeOfFirstRequest: number;
|
||||
private currentInvocationId;
|
||||
/**
|
||||
* A cache of buffers written to this instance, ready for consuming
|
||||
*/
|
||||
private writeBuffers;
|
||||
private numChunksReadInRequest;
|
||||
/**
|
||||
* An array of buffers used for caching the most recent upload chunk.
|
||||
* We should not assume that the server received all bytes sent in the request.
|
||||
* - https://cloud.google.com/storage/docs/performing-resumable-uploads#chunked-upload
|
||||
*/
|
||||
private localWriteCache;
|
||||
private localWriteCacheByteLength;
|
||||
private upstreamEnded;
|
||||
constructor(cfg: UploadConfig);
|
||||
/**
|
||||
* Prevent 'finish' event until the upload has succeeded.
|
||||
*
|
||||
* @param fireFinishEvent The finish callback
|
||||
*/
|
||||
_final(fireFinishEvent?: () => void): void;
|
||||
/**
|
||||
* Handles incoming data from upstream
|
||||
*
|
||||
* @param chunk The chunk to append to the buffer
|
||||
* @param encoding The encoding of the chunk
|
||||
* @param readCallback A callback for when the buffer has been read downstream
|
||||
*/
|
||||
_write(chunk: Buffer | string, encoding: BufferEncoding, readCallback?: () => void): void;
|
||||
/**
|
||||
* Prepends the local buffer to write buffer and resets it.
|
||||
*
|
||||
* @param keepLastBytes number of bytes to keep from the end of the local buffer.
|
||||
*/
|
||||
private prependLocalBufferToUpstream;
|
||||
/**
|
||||
* Retrieves data from upstream's buffer.
|
||||
*
|
||||
* @param limit The maximum amount to return from the buffer.
|
||||
* @returns The data requested.
|
||||
*/
|
||||
private pullFromChunkBuffer;
|
||||
/**
|
||||
* A handler for determining if data is ready to be read from upstream.
|
||||
*
|
||||
* @returns If there will be more chunks to read in the future
|
||||
*/
|
||||
private waitForNextChunk;
|
||||
/**
|
||||
* Reads data from upstream up to the provided `limit`.
|
||||
* Ends when the limit has reached or no data is expected to be pushed from upstream.
|
||||
*
|
||||
* @param limit The most amount of data this iterator should return. `Infinity` by default.
|
||||
*/
|
||||
private upstreamIterator;
|
||||
createURI(): Promise<string>;
|
||||
createURI(callback: CreateUriCallback): void;
|
||||
protected createURIAsync(): Promise<string>;
|
||||
private continueUploading;
|
||||
startUploading(): Promise<void>;
|
||||
private responseHandler;
|
||||
private getAndSetOffset;
|
||||
private makeRequest;
|
||||
private makeRequestStream;
|
||||
/**
|
||||
* @return {bool} is the request good?
|
||||
*/
|
||||
private onResponse;
|
||||
/**
|
||||
* @param resp GaxiosResponse object from previous attempt
|
||||
*/
|
||||
private attemptDelayedRetry;
|
||||
/**
|
||||
* @returns {number} the amount of time to wait before retrying the request
|
||||
*/
|
||||
private getRetryDelay;
|
||||
private sanitizeEndpoint;
|
||||
/**
|
||||
* Check if a given status code is 2xx
|
||||
*
|
||||
* @param status The status code to check
|
||||
* @returns if the status is 2xx
|
||||
*/
|
||||
isSuccessfulResponse(status: number): boolean;
|
||||
}
|
||||
export declare function upload(cfg: UploadConfig): Upload;
|
||||
export declare function createURI(cfg: UploadConfig): Promise<string>;
|
||||
export declare function createURI(cfg: UploadConfig, callback: CreateUriCallback): void;
|
||||
@ -0,0 +1,746 @@
|
||||
"use strict";
|
||||
// Copyright 2022 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
|
||||
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
|
||||
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
||||
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
||||
};
|
||||
var _Upload_instances, _Upload_resetLocalBuffersCache, _Upload_addLocalBufferCache;
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.createURI = exports.upload = exports.Upload = exports.PROTOCOL_REGEX = void 0;
|
||||
const abort_controller_1 = require("abort-controller");
|
||||
const crypto_1 = require("crypto");
|
||||
const extend = require("extend");
|
||||
const gaxios = require("gaxios");
|
||||
const google_auth_library_1 = require("google-auth-library");
|
||||
const stream_1 = require("stream");
|
||||
const retry = require("async-retry");
|
||||
const uuid = require("uuid");
|
||||
const NOT_FOUND_STATUS_CODE = 404;
|
||||
const RESUMABLE_INCOMPLETE_STATUS_CODE = 308;
|
||||
const DEFAULT_API_ENDPOINT_REGEX = /.*\.googleapis\.com/;
|
||||
const packageJson = require('../../package.json');
|
||||
exports.PROTOCOL_REGEX = /^(\w*):\/\//;
|
||||
class Upload extends stream_1.Writable {
|
||||
constructor(cfg) {
|
||||
super(cfg);
|
||||
_Upload_instances.add(this);
|
||||
this.numBytesWritten = 0;
|
||||
this.numRetries = 0;
|
||||
this.currentInvocationId = {
|
||||
chunk: uuid.v4(),
|
||||
uri: uuid.v4(),
|
||||
offset: uuid.v4(),
|
||||
};
|
||||
/**
|
||||
* A cache of buffers written to this instance, ready for consuming
|
||||
*/
|
||||
this.writeBuffers = [];
|
||||
this.numChunksReadInRequest = 0;
|
||||
/**
|
||||
* An array of buffers used for caching the most recent upload chunk.
|
||||
* We should not assume that the server received all bytes sent in the request.
|
||||
* - https://cloud.google.com/storage/docs/performing-resumable-uploads#chunked-upload
|
||||
*/
|
||||
this.localWriteCache = [];
|
||||
this.localWriteCacheByteLength = 0;
|
||||
this.upstreamEnded = false;
|
||||
cfg = cfg || {};
|
||||
if (!cfg.bucket || !cfg.file) {
|
||||
throw new Error('A bucket and file name are required');
|
||||
}
|
||||
cfg.authConfig = cfg.authConfig || {};
|
||||
cfg.authConfig.scopes = [
|
||||
'https://www.googleapis.com/auth/devstorage.full_control',
|
||||
];
|
||||
this.authClient = cfg.authClient || new google_auth_library_1.GoogleAuth(cfg.authConfig);
|
||||
this.apiEndpoint = 'https://storage.googleapis.com';
|
||||
if (cfg.apiEndpoint) {
|
||||
this.apiEndpoint = this.sanitizeEndpoint(cfg.apiEndpoint);
|
||||
if (!DEFAULT_API_ENDPOINT_REGEX.test(cfg.apiEndpoint)) {
|
||||
this.authClient = gaxios;
|
||||
}
|
||||
}
|
||||
this.baseURI = `${this.apiEndpoint}/upload/storage/v1/b`;
|
||||
this.bucket = cfg.bucket;
|
||||
const cacheKeyElements = [cfg.bucket, cfg.file];
|
||||
if (typeof cfg.generation === 'number') {
|
||||
cacheKeyElements.push(`${cfg.generation}`);
|
||||
}
|
||||
this.cacheKey = cacheKeyElements.join('/');
|
||||
this.customRequestOptions = cfg.customRequestOptions || {};
|
||||
this.file = cfg.file;
|
||||
this.generation = cfg.generation;
|
||||
this.kmsKeyName = cfg.kmsKeyName;
|
||||
this.metadata = cfg.metadata || {};
|
||||
this.offset = cfg.offset;
|
||||
this.origin = cfg.origin;
|
||||
this.params = cfg.params || {};
|
||||
this.userProject = cfg.userProject;
|
||||
this.chunkSize = cfg.chunkSize;
|
||||
this.retryOptions = cfg.retryOptions;
|
||||
if (cfg.key) {
|
||||
const base64Key = Buffer.from(cfg.key).toString('base64');
|
||||
this.encryption = {
|
||||
key: base64Key,
|
||||
hash: (0, crypto_1.createHash)('sha256').update(cfg.key).digest('base64'),
|
||||
};
|
||||
}
|
||||
this.predefinedAcl = cfg.predefinedAcl;
|
||||
if (cfg.private)
|
||||
this.predefinedAcl = 'private';
|
||||
if (cfg.public)
|
||||
this.predefinedAcl = 'publicRead';
|
||||
const autoRetry = cfg.retryOptions.autoRetry;
|
||||
this.uriProvidedManually = !!cfg.uri;
|
||||
this.uri = cfg.uri;
|
||||
this.numBytesWritten = 0;
|
||||
this.numRetries = 0; // counter for number of retries currently executed
|
||||
if (!autoRetry) {
|
||||
cfg.retryOptions.maxRetries = 0;
|
||||
}
|
||||
this.timeOfFirstRequest = Date.now();
|
||||
const contentLength = cfg.metadata
|
||||
? Number(cfg.metadata.contentLength)
|
||||
: NaN;
|
||||
this.contentLength = isNaN(contentLength) ? '*' : contentLength;
|
||||
this.once('writing', () => {
|
||||
if (this.uri) {
|
||||
this.continueUploading();
|
||||
}
|
||||
else {
|
||||
this.createURI(err => {
|
||||
if (err) {
|
||||
return this.destroy(err);
|
||||
}
|
||||
this.startUploading();
|
||||
return;
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
/**
|
||||
* Prevent 'finish' event until the upload has succeeded.
|
||||
*
|
||||
* @param fireFinishEvent The finish callback
|
||||
*/
|
||||
_final(fireFinishEvent = () => { }) {
|
||||
this.upstreamEnded = true;
|
||||
this.once('uploadFinished', fireFinishEvent);
|
||||
process.nextTick(() => {
|
||||
this.emit('upstreamFinished');
|
||||
// it's possible `_write` may not be called - namely for empty object uploads
|
||||
this.emit('writing');
|
||||
});
|
||||
}
|
||||
/**
|
||||
* Handles incoming data from upstream
|
||||
*
|
||||
* @param chunk The chunk to append to the buffer
|
||||
* @param encoding The encoding of the chunk
|
||||
* @param readCallback A callback for when the buffer has been read downstream
|
||||
*/
|
||||
_write(chunk, encoding, readCallback = () => { }) {
|
||||
// Backwards-compatible event
|
||||
this.emit('writing');
|
||||
this.writeBuffers.push(typeof chunk === 'string' ? Buffer.from(chunk, encoding) : chunk);
|
||||
this.once('readFromChunkBuffer', readCallback);
|
||||
process.nextTick(() => this.emit('wroteToChunkBuffer'));
|
||||
}
|
||||
/**
|
||||
* Prepends the local buffer to write buffer and resets it.
|
||||
*
|
||||
* @param keepLastBytes number of bytes to keep from the end of the local buffer.
|
||||
*/
|
||||
prependLocalBufferToUpstream(keepLastBytes) {
|
||||
// Typically, the upstream write buffers should be smaller than the local
|
||||
// cache, so we can save time by setting the local cache as the new
|
||||
// upstream write buffer array and appending the old array to it
|
||||
let initialBuffers = [];
|
||||
if (keepLastBytes) {
|
||||
// we only want the last X bytes
|
||||
let bytesKept = 0;
|
||||
while (keepLastBytes > bytesKept) {
|
||||
// load backwards because we want the last X bytes
|
||||
// note: `localWriteCacheByteLength` is reset below
|
||||
let buf = this.localWriteCache.pop();
|
||||
if (!buf)
|
||||
break;
|
||||
bytesKept += buf.byteLength;
|
||||
if (bytesKept > keepLastBytes) {
|
||||
// we have gone over the amount desired, let's keep the last X bytes
|
||||
// of this buffer
|
||||
const diff = bytesKept - keepLastBytes;
|
||||
buf = buf.subarray(diff);
|
||||
bytesKept -= diff;
|
||||
}
|
||||
initialBuffers.unshift(buf);
|
||||
}
|
||||
}
|
||||
else {
|
||||
// we're keeping all of the local cache, simply use it as the initial buffer
|
||||
initialBuffers = this.localWriteCache;
|
||||
}
|
||||
// Append the old upstream to the new
|
||||
const append = this.writeBuffers;
|
||||
this.writeBuffers = initialBuffers;
|
||||
for (const buf of append) {
|
||||
this.writeBuffers.push(buf);
|
||||
}
|
||||
// reset last buffers sent
|
||||
__classPrivateFieldGet(this, _Upload_instances, "m", _Upload_resetLocalBuffersCache).call(this);
|
||||
}
|
||||
/**
|
||||
* Retrieves data from upstream's buffer.
|
||||
*
|
||||
* @param limit The maximum amount to return from the buffer.
|
||||
* @returns The data requested.
|
||||
*/
|
||||
*pullFromChunkBuffer(limit) {
|
||||
while (limit) {
|
||||
const buf = this.writeBuffers.shift();
|
||||
if (!buf)
|
||||
break;
|
||||
let bufToYield = buf;
|
||||
if (buf.byteLength > limit) {
|
||||
bufToYield = buf.subarray(0, limit);
|
||||
this.writeBuffers.unshift(buf.subarray(limit));
|
||||
limit = 0;
|
||||
}
|
||||
else {
|
||||
limit -= buf.byteLength;
|
||||
}
|
||||
yield bufToYield;
|
||||
// Notify upstream we've read from the buffer and we're able to consume
|
||||
// more. It can also potentially send more data down as we're currently
|
||||
// iterating.
|
||||
this.emit('readFromChunkBuffer');
|
||||
}
|
||||
}
|
||||
/**
|
||||
* A handler for determining if data is ready to be read from upstream.
|
||||
*
|
||||
* @returns If there will be more chunks to read in the future
|
||||
*/
|
||||
async waitForNextChunk() {
|
||||
const willBeMoreChunks = await new Promise(resolve => {
|
||||
// There's data available - it should be digested
|
||||
if (this.writeBuffers.length) {
|
||||
return resolve(true);
|
||||
}
|
||||
// The upstream writable ended, we shouldn't expect any more data.
|
||||
if (this.upstreamEnded) {
|
||||
return resolve(false);
|
||||
}
|
||||
// Nothing immediate seems to be determined. We need to prepare some
|
||||
// listeners to determine next steps...
|
||||
const wroteToChunkBufferCallback = () => {
|
||||
removeListeners();
|
||||
return resolve(true);
|
||||
};
|
||||
const upstreamFinishedCallback = () => {
|
||||
removeListeners();
|
||||
// this should be the last chunk, if there's anything there
|
||||
if (this.writeBuffers.length)
|
||||
return resolve(true);
|
||||
return resolve(false);
|
||||
};
|
||||
// Remove listeners when we're ready to callback.
|
||||
const removeListeners = () => {
|
||||
this.removeListener('wroteToChunkBuffer', wroteToChunkBufferCallback);
|
||||
this.removeListener('upstreamFinished', upstreamFinishedCallback);
|
||||
};
|
||||
// If there's data recently written it should be digested
|
||||
this.once('wroteToChunkBuffer', wroteToChunkBufferCallback);
|
||||
// If the upstream finishes let's see if there's anything to grab
|
||||
this.once('upstreamFinished', upstreamFinishedCallback);
|
||||
});
|
||||
return willBeMoreChunks;
|
||||
}
|
||||
/**
|
||||
* Reads data from upstream up to the provided `limit`.
|
||||
* Ends when the limit has reached or no data is expected to be pushed from upstream.
|
||||
*
|
||||
* @param limit The most amount of data this iterator should return. `Infinity` by default.
|
||||
*/
|
||||
async *upstreamIterator(limit = Infinity) {
|
||||
// read from upstream chunk buffer
|
||||
while (limit && (await this.waitForNextChunk())) {
|
||||
// read until end or limit has been reached
|
||||
for (const chunk of this.pullFromChunkBuffer(limit)) {
|
||||
limit -= chunk.byteLength;
|
||||
yield chunk;
|
||||
}
|
||||
}
|
||||
}
|
||||
createURI(callback) {
|
||||
if (!callback) {
|
||||
return this.createURIAsync();
|
||||
}
|
||||
this.createURIAsync().then(r => callback(null, r), callback);
|
||||
}
|
||||
async createURIAsync() {
|
||||
const metadata = { ...this.metadata };
|
||||
const headers = {};
|
||||
// Delete content length and content type from metadata if they exist.
|
||||
// These are headers and should not be sent as part of the metadata.
|
||||
if (metadata.contentLength) {
|
||||
headers['X-Upload-Content-Length'] = metadata.contentLength.toString();
|
||||
delete metadata.contentLength;
|
||||
}
|
||||
if (metadata.contentType) {
|
||||
headers['X-Upload-Content-Type'] = metadata.contentType;
|
||||
delete metadata.contentType;
|
||||
}
|
||||
// Check if headers already exist before creating new ones
|
||||
const reqOpts = {
|
||||
method: 'POST',
|
||||
url: [this.baseURI, this.bucket, 'o'].join('/'),
|
||||
params: Object.assign({
|
||||
name: this.file,
|
||||
uploadType: 'resumable',
|
||||
}, this.params),
|
||||
data: metadata,
|
||||
headers: {
|
||||
'x-goog-api-client': `gl-node/${process.versions.node} gccl/${packageJson.version} gccl-invocation-id/${this.currentInvocationId.uri}`,
|
||||
...headers,
|
||||
},
|
||||
};
|
||||
if (metadata.contentLength) {
|
||||
reqOpts.headers['X-Upload-Content-Length'] =
|
||||
metadata.contentLength.toString();
|
||||
}
|
||||
if (metadata.contentType) {
|
||||
reqOpts.headers['X-Upload-Content-Type'] = metadata.contentType;
|
||||
}
|
||||
if (typeof this.generation !== 'undefined') {
|
||||
reqOpts.params.ifGenerationMatch = this.generation;
|
||||
}
|
||||
if (this.kmsKeyName) {
|
||||
reqOpts.params.kmsKeyName = this.kmsKeyName;
|
||||
}
|
||||
if (this.predefinedAcl) {
|
||||
reqOpts.params.predefinedAcl = this.predefinedAcl;
|
||||
}
|
||||
if (this.origin) {
|
||||
reqOpts.headers.Origin = this.origin;
|
||||
}
|
||||
const uri = await retry(async (bail) => {
|
||||
var _a, _b, _c;
|
||||
try {
|
||||
const res = await this.makeRequest(reqOpts);
|
||||
// We have successfully got a URI we can now create a new invocation id
|
||||
this.currentInvocationId.uri = uuid.v4();
|
||||
return res.headers.location;
|
||||
}
|
||||
catch (err) {
|
||||
const e = err;
|
||||
const apiError = {
|
||||
code: (_a = e.response) === null || _a === void 0 ? void 0 : _a.status,
|
||||
name: (_b = e.response) === null || _b === void 0 ? void 0 : _b.statusText,
|
||||
message: (_c = e.response) === null || _c === void 0 ? void 0 : _c.statusText,
|
||||
errors: [
|
||||
{
|
||||
reason: e.code,
|
||||
},
|
||||
],
|
||||
};
|
||||
if (this.retryOptions.maxRetries > 0 &&
|
||||
this.retryOptions.retryableErrorFn(apiError)) {
|
||||
throw e;
|
||||
}
|
||||
else {
|
||||
return bail(e);
|
||||
}
|
||||
}
|
||||
}, {
|
||||
retries: this.retryOptions.maxRetries,
|
||||
factor: this.retryOptions.retryDelayMultiplier,
|
||||
maxTimeout: this.retryOptions.maxRetryDelay * 1000,
|
||||
maxRetryTime: this.retryOptions.totalTimeout * 1000, //convert to milliseconds
|
||||
});
|
||||
this.uri = uri;
|
||||
this.offset = 0;
|
||||
return uri;
|
||||
}
|
||||
async continueUploading() {
|
||||
if (typeof this.offset === 'number') {
|
||||
this.startUploading();
|
||||
return;
|
||||
}
|
||||
await this.getAndSetOffset();
|
||||
this.startUploading();
|
||||
}
|
||||
async startUploading() {
|
||||
const multiChunkMode = !!this.chunkSize;
|
||||
let responseReceived = false;
|
||||
this.numChunksReadInRequest = 0;
|
||||
if (!this.offset) {
|
||||
this.offset = 0;
|
||||
}
|
||||
// Check if the offset (server) is too far behind the current stream
|
||||
if (this.offset < this.numBytesWritten) {
|
||||
const delta = this.numBytesWritten - this.offset;
|
||||
const message = `The offset is lower than the number of bytes written. The server has ${this.offset} bytes and while ${this.numBytesWritten} bytes has been uploaded - thus ${delta} bytes are missing. Stopping as this could result in data loss. Initiate a new upload to continue.`;
|
||||
this.emit('error', new RangeError(message));
|
||||
return;
|
||||
}
|
||||
// Check if we should 'fast-forward' to the relevant data to upload
|
||||
if (this.numBytesWritten < this.offset) {
|
||||
// 'fast-forward' to the byte where we need to upload.
|
||||
// only push data from the byte after the one we left off on
|
||||
const fastForwardBytes = this.offset - this.numBytesWritten;
|
||||
for await (const _chunk of this.upstreamIterator(fastForwardBytes)) {
|
||||
_chunk; // discard the data up until the point we want
|
||||
}
|
||||
this.numBytesWritten = this.offset;
|
||||
}
|
||||
let expectedUploadSize = undefined;
|
||||
// Set `expectedUploadSize` to `contentLength - this.numBytesWritten`, if available
|
||||
if (typeof this.contentLength === 'number') {
|
||||
expectedUploadSize = this.contentLength - this.numBytesWritten;
|
||||
}
|
||||
// `expectedUploadSize` should be no more than the `chunkSize`.
|
||||
// It's possible this is the last chunk request for a multiple
|
||||
// chunk upload, thus smaller than the chunk size.
|
||||
if (this.chunkSize) {
|
||||
expectedUploadSize = expectedUploadSize
|
||||
? Math.min(this.chunkSize, expectedUploadSize)
|
||||
: this.chunkSize;
|
||||
}
|
||||
// A queue for the upstream data
|
||||
const upstreamQueue = this.upstreamIterator(expectedUploadSize);
|
||||
// The primary read stream for this request. This stream retrieves no more
|
||||
// than the exact requested amount from upstream.
|
||||
const requestStream = new stream_1.Readable({
|
||||
read: async () => {
|
||||
// Don't attempt to retrieve data upstream if we already have a response
|
||||
if (responseReceived)
|
||||
requestStream.push(null);
|
||||
const result = await upstreamQueue.next();
|
||||
if (result.value) {
|
||||
this.numChunksReadInRequest++;
|
||||
if (multiChunkMode) {
|
||||
// save ever buffer used in the request in multi-chunk mode
|
||||
__classPrivateFieldGet(this, _Upload_instances, "m", _Upload_addLocalBufferCache).call(this, result.value);
|
||||
}
|
||||
else {
|
||||
__classPrivateFieldGet(this, _Upload_instances, "m", _Upload_resetLocalBuffersCache).call(this);
|
||||
__classPrivateFieldGet(this, _Upload_instances, "m", _Upload_addLocalBufferCache).call(this, result.value);
|
||||
}
|
||||
this.numBytesWritten += result.value.byteLength;
|
||||
this.emit('progress', {
|
||||
bytesWritten: this.numBytesWritten,
|
||||
contentLength: this.contentLength,
|
||||
});
|
||||
requestStream.push(result.value);
|
||||
}
|
||||
if (result.done) {
|
||||
requestStream.push(null);
|
||||
}
|
||||
},
|
||||
});
|
||||
const headers = {
|
||||
'x-goog-api-client': `gl-node/${process.versions.node} gccl/${packageJson.version} gccl-invocation-id/${this.currentInvocationId.chunk}`,
|
||||
};
|
||||
// If using multiple chunk upload, set appropriate header
|
||||
if (multiChunkMode) {
|
||||
// We need to know how much data is available upstream to set the `Content-Range` header.
|
||||
// https://cloud.google.com/storage/docs/performing-resumable-uploads#chunked-upload
|
||||
for await (const chunk of this.upstreamIterator(expectedUploadSize)) {
|
||||
// This will conveniently track and keep the size of the buffers
|
||||
__classPrivateFieldGet(this, _Upload_instances, "m", _Upload_addLocalBufferCache).call(this, chunk);
|
||||
}
|
||||
// We hit either the expected upload size or the remainder
|
||||
const bytesToUpload = this.localWriteCacheByteLength;
|
||||
// Important: we want to know if the upstream has ended and the queue is empty before
|
||||
// unshifting data back into the queue. This way we will know if this is the last request or not.
|
||||
const isLastChunkOfUpload = !(await this.waitForNextChunk());
|
||||
// Important: put the data back in the queue for the actual upload
|
||||
this.prependLocalBufferToUpstream();
|
||||
let totalObjectSize = this.contentLength;
|
||||
if (typeof this.contentLength !== 'number' && isLastChunkOfUpload) {
|
||||
// Let's let the server know this is the last chunk since
|
||||
// we didn't know the content-length beforehand.
|
||||
totalObjectSize = bytesToUpload + this.numBytesWritten;
|
||||
}
|
||||
// `- 1` as the ending byte is inclusive in the request.
|
||||
const endingByte = bytesToUpload + this.numBytesWritten - 1;
|
||||
// `Content-Length` for multiple chunk uploads is the size of the chunk,
|
||||
// not the overall object
|
||||
headers['Content-Length'] = bytesToUpload;
|
||||
headers['Content-Range'] = `bytes ${this.offset}-${endingByte}/${totalObjectSize}`;
|
||||
}
|
||||
else {
|
||||
headers['Content-Range'] = `bytes ${this.offset}-*/${this.contentLength}`;
|
||||
}
|
||||
const reqOpts = {
|
||||
method: 'PUT',
|
||||
url: this.uri,
|
||||
headers,
|
||||
body: requestStream,
|
||||
};
|
||||
try {
|
||||
const resp = await this.makeRequestStream(reqOpts);
|
||||
if (resp) {
|
||||
responseReceived = true;
|
||||
this.responseHandler(resp);
|
||||
}
|
||||
}
|
||||
catch (e) {
|
||||
const err = e;
|
||||
if (this.retryOptions.retryableErrorFn(err)) {
|
||||
this.attemptDelayedRetry({
|
||||
status: NaN,
|
||||
data: err,
|
||||
});
|
||||
return;
|
||||
}
|
||||
this.destroy(err);
|
||||
}
|
||||
}
|
||||
// Process the API response to look for errors that came in
|
||||
// the response body.
|
||||
responseHandler(resp) {
|
||||
if (resp.data.error) {
|
||||
this.destroy(resp.data.error);
|
||||
return;
|
||||
}
|
||||
// At this point we can safely create a new id for the chunk
|
||||
this.currentInvocationId.chunk = uuid.v4();
|
||||
const shouldContinueWithNextMultiChunkRequest = this.chunkSize &&
|
||||
resp.status === RESUMABLE_INCOMPLETE_STATUS_CODE &&
|
||||
resp.headers.range;
|
||||
if (shouldContinueWithNextMultiChunkRequest) {
|
||||
// Use the upper value in this header to determine where to start the next chunk.
|
||||
// We should not assume that the server received all bytes sent in the request.
|
||||
// https://cloud.google.com/storage/docs/performing-resumable-uploads#chunked-upload
|
||||
const range = resp.headers.range;
|
||||
this.offset = Number(range.split('-')[1]) + 1;
|
||||
// We should not assume that the server received all bytes sent in the request.
|
||||
// - https://cloud.google.com/storage/docs/performing-resumable-uploads#chunked-upload
|
||||
const missingBytes = this.numBytesWritten - this.offset;
|
||||
if (missingBytes) {
|
||||
// As multi-chunk uploads send one chunk per request and pulls one
|
||||
// chunk into the pipeline, prepending the missing bytes back should
|
||||
// be fine for the next request.
|
||||
this.prependLocalBufferToUpstream(missingBytes);
|
||||
this.numBytesWritten -= missingBytes;
|
||||
}
|
||||
else {
|
||||
// No bytes missing - no need to keep the local cache
|
||||
__classPrivateFieldGet(this, _Upload_instances, "m", _Upload_resetLocalBuffersCache).call(this);
|
||||
}
|
||||
// continue uploading next chunk
|
||||
this.continueUploading();
|
||||
}
|
||||
else if (!this.isSuccessfulResponse(resp.status)) {
|
||||
const err = new Error('Upload failed');
|
||||
err.code = resp.status;
|
||||
err.name = 'Upload failed';
|
||||
if (resp === null || resp === void 0 ? void 0 : resp.data) {
|
||||
err.errors = [resp === null || resp === void 0 ? void 0 : resp.data];
|
||||
}
|
||||
this.destroy(err);
|
||||
}
|
||||
else {
|
||||
// no need to keep the cache
|
||||
__classPrivateFieldGet(this, _Upload_instances, "m", _Upload_resetLocalBuffersCache).call(this);
|
||||
if (resp && resp.data) {
|
||||
resp.data.size = Number(resp.data.size);
|
||||
}
|
||||
this.emit('metadata', resp.data);
|
||||
// Allow the object (Upload) to continue naturally so the user's
|
||||
// "finish" event fires.
|
||||
this.emit('uploadFinished');
|
||||
}
|
||||
}
|
||||
async getAndSetOffset() {
|
||||
const opts = {
|
||||
method: 'PUT',
|
||||
url: this.uri,
|
||||
headers: {
|
||||
'Content-Length': 0,
|
||||
'Content-Range': 'bytes */*',
|
||||
'x-goog-api-client': `gl-node/${process.versions.node} gccl/${packageJson.version} gccl-invocation-id/${this.currentInvocationId.offset}`,
|
||||
},
|
||||
};
|
||||
try {
|
||||
const resp = await this.makeRequest(opts);
|
||||
// Successfully got the offset we can now create a new offset invocation id
|
||||
this.currentInvocationId.offset = uuid.v4();
|
||||
if (resp.status === RESUMABLE_INCOMPLETE_STATUS_CODE) {
|
||||
if (resp.headers.range) {
|
||||
const range = resp.headers.range;
|
||||
this.offset = Number(range.split('-')[1]) + 1;
|
||||
return;
|
||||
}
|
||||
}
|
||||
this.offset = 0;
|
||||
}
|
||||
catch (e) {
|
||||
const err = e;
|
||||
if (this.retryOptions.retryableErrorFn(err)) {
|
||||
this.attemptDelayedRetry({
|
||||
status: NaN,
|
||||
data: err,
|
||||
});
|
||||
return;
|
||||
}
|
||||
this.destroy(err);
|
||||
}
|
||||
}
|
||||
async makeRequest(reqOpts) {
|
||||
if (this.encryption) {
|
||||
reqOpts.headers = reqOpts.headers || {};
|
||||
reqOpts.headers['x-goog-encryption-algorithm'] = 'AES256';
|
||||
reqOpts.headers['x-goog-encryption-key'] = this.encryption.key.toString();
|
||||
reqOpts.headers['x-goog-encryption-key-sha256'] =
|
||||
this.encryption.hash.toString();
|
||||
}
|
||||
if (this.userProject) {
|
||||
reqOpts.params = reqOpts.params || {};
|
||||
reqOpts.params.userProject = this.userProject;
|
||||
}
|
||||
// Let gaxios know we will handle a 308 error code ourselves.
|
||||
reqOpts.validateStatus = (status) => {
|
||||
return (this.isSuccessfulResponse(status) ||
|
||||
status === RESUMABLE_INCOMPLETE_STATUS_CODE);
|
||||
};
|
||||
const combinedReqOpts = extend(true, {}, this.customRequestOptions, reqOpts);
|
||||
const res = await this.authClient.request(combinedReqOpts);
|
||||
if (res.data && res.data.error) {
|
||||
throw res.data.error;
|
||||
}
|
||||
return res;
|
||||
}
|
||||
async makeRequestStream(reqOpts) {
|
||||
const controller = new abort_controller_1.default();
|
||||
const errorCallback = () => controller.abort();
|
||||
this.once('error', errorCallback);
|
||||
if (this.userProject) {
|
||||
reqOpts.params = reqOpts.params || {};
|
||||
reqOpts.params.userProject = this.userProject;
|
||||
}
|
||||
reqOpts.signal = controller.signal;
|
||||
reqOpts.validateStatus = () => true;
|
||||
const combinedReqOpts = extend(true, {}, this.customRequestOptions, reqOpts);
|
||||
const res = await this.authClient.request(combinedReqOpts);
|
||||
const successfulRequest = this.onResponse(res);
|
||||
this.removeListener('error', errorCallback);
|
||||
return successfulRequest ? res : null;
|
||||
}
|
||||
/**
|
||||
* @return {bool} is the request good?
|
||||
*/
|
||||
onResponse(resp) {
|
||||
if (resp.status !== 200 &&
|
||||
this.retryOptions.retryableErrorFn({
|
||||
code: resp.status,
|
||||
message: resp.statusText,
|
||||
name: resp.statusText,
|
||||
})) {
|
||||
this.attemptDelayedRetry(resp);
|
||||
return false;
|
||||
}
|
||||
this.emit('response', resp);
|
||||
return true;
|
||||
}
|
||||
/**
|
||||
* @param resp GaxiosResponse object from previous attempt
|
||||
*/
|
||||
attemptDelayedRetry(resp) {
|
||||
if (this.numRetries < this.retryOptions.maxRetries) {
|
||||
if (resp.status === NOT_FOUND_STATUS_CODE &&
|
||||
this.numChunksReadInRequest === 0) {
|
||||
this.startUploading();
|
||||
}
|
||||
else {
|
||||
const retryDelay = this.getRetryDelay();
|
||||
if (retryDelay <= 0) {
|
||||
this.destroy(new Error(`Retry total time limit exceeded - ${resp.data}`));
|
||||
return;
|
||||
}
|
||||
// Unshift the local cache back in case it's needed for the next request.
|
||||
this.numBytesWritten -= this.localWriteCacheByteLength;
|
||||
this.prependLocalBufferToUpstream();
|
||||
// We don't know how much data has been received by the server.
|
||||
// `continueUploading` will recheck the offset via `getAndSetOffset`.
|
||||
// If `offset` < `numberBytesReceived` then we will raise a RangeError
|
||||
// as we've streamed too much data that has been missed - this should
|
||||
// not be the case for multi-chunk uploads as `lastChunkSent` is the
|
||||
// body of the entire request.
|
||||
this.offset = undefined;
|
||||
setTimeout(this.continueUploading.bind(this), retryDelay);
|
||||
}
|
||||
this.numRetries++;
|
||||
}
|
||||
else {
|
||||
this.destroy(new Error('Retry limit exceeded - ' + resp.data));
|
||||
}
|
||||
}
|
||||
/**
|
||||
* @returns {number} the amount of time to wait before retrying the request
|
||||
*/
|
||||
getRetryDelay() {
|
||||
const randomMs = Math.round(Math.random() * 1000);
|
||||
const waitTime = Math.pow(this.retryOptions.retryDelayMultiplier, this.numRetries) *
|
||||
1000 +
|
||||
randomMs;
|
||||
const maxAllowableDelayMs = this.retryOptions.totalTimeout * 1000 -
|
||||
(Date.now() - this.timeOfFirstRequest);
|
||||
const maxRetryDelayMs = this.retryOptions.maxRetryDelay * 1000;
|
||||
return Math.min(waitTime, maxRetryDelayMs, maxAllowableDelayMs);
|
||||
}
|
||||
/*
|
||||
* Prepare user-defined API endpoint for compatibility with our API.
|
||||
*/
|
||||
sanitizeEndpoint(url) {
|
||||
if (!exports.PROTOCOL_REGEX.test(url)) {
|
||||
url = `https://${url}`;
|
||||
}
|
||||
return url.replace(/\/+$/, ''); // Remove trailing slashes
|
||||
}
|
||||
/**
|
||||
* Check if a given status code is 2xx
|
||||
*
|
||||
* @param status The status code to check
|
||||
* @returns if the status is 2xx
|
||||
*/
|
||||
isSuccessfulResponse(status) {
|
||||
return status >= 200 && status < 300;
|
||||
}
|
||||
}
|
||||
exports.Upload = Upload;
|
||||
_Upload_instances = new WeakSet(), _Upload_resetLocalBuffersCache = function _Upload_resetLocalBuffersCache() {
|
||||
this.localWriteCache = [];
|
||||
this.localWriteCacheByteLength = 0;
|
||||
}, _Upload_addLocalBufferCache = function _Upload_addLocalBufferCache(buf) {
|
||||
this.localWriteCache.push(buf);
|
||||
this.localWriteCacheByteLength += buf.byteLength;
|
||||
};
|
||||
function upload(cfg) {
|
||||
return new Upload(cfg);
|
||||
}
|
||||
exports.upload = upload;
|
||||
function createURI(cfg, callback) {
|
||||
const up = new Upload(cfg);
|
||||
if (!callback) {
|
||||
return up.createURI();
|
||||
}
|
||||
up.createURI().then(r => callback(null, r), callback);
|
||||
}
|
||||
exports.createURI = createURI;
|
||||
//# sourceMappingURL=resumable-upload.js.map
|
||||
@ -0,0 +1,94 @@
|
||||
/// <reference types="node" />
|
||||
import * as http from 'http';
|
||||
interface GetCredentialsResponse {
|
||||
client_email?: string;
|
||||
}
|
||||
export interface AuthClient {
|
||||
sign(blobToSign: string): Promise<string>;
|
||||
getCredentials(): Promise<GetCredentialsResponse>;
|
||||
}
|
||||
export interface BucketI {
|
||||
name: string;
|
||||
}
|
||||
export interface FileI {
|
||||
name: string;
|
||||
}
|
||||
export interface Query {
|
||||
[key: string]: string;
|
||||
}
|
||||
export interface GetSignedUrlConfigInternal {
|
||||
expiration: number;
|
||||
accessibleAt?: Date;
|
||||
method: string;
|
||||
extensionHeaders?: http.OutgoingHttpHeaders;
|
||||
queryParams?: Query;
|
||||
cname?: string;
|
||||
contentMd5?: string;
|
||||
contentType?: string;
|
||||
bucket: string;
|
||||
file?: string;
|
||||
}
|
||||
export interface SignerGetSignedUrlConfig {
|
||||
method: 'GET' | 'PUT' | 'DELETE' | 'POST';
|
||||
expires: string | number | Date;
|
||||
accessibleAt?: string | number | Date;
|
||||
virtualHostedStyle?: boolean;
|
||||
version?: 'v2' | 'v4';
|
||||
cname?: string;
|
||||
extensionHeaders?: http.OutgoingHttpHeaders;
|
||||
queryParams?: Query;
|
||||
contentMd5?: string;
|
||||
contentType?: string;
|
||||
}
|
||||
export type SignerGetSignedUrlResponse = string;
|
||||
export type GetSignedUrlResponse = [SignerGetSignedUrlResponse];
|
||||
export interface GetSignedUrlCallback {
|
||||
(err: Error | null, url?: string): void;
|
||||
}
|
||||
export declare enum SignerExceptionMessages {
|
||||
ACCESSIBLE_DATE_INVALID = "The accessible at date provided was invalid.",
|
||||
EXPIRATION_BEFORE_ACCESSIBLE_DATE = "An expiration date cannot be before accessible date.",
|
||||
X_GOOG_CONTENT_SHA256 = "The header X-Goog-Content-SHA256 must be a hexadecimal string."
|
||||
}
|
||||
/**
|
||||
* @const {string}
|
||||
* @private
|
||||
*/
|
||||
export declare const PATH_STYLED_HOST = "https://storage.googleapis.com";
|
||||
export declare class URLSigner {
|
||||
private authClient;
|
||||
private bucket;
|
||||
private file?;
|
||||
constructor(authClient: AuthClient, bucket: BucketI, file?: FileI);
|
||||
getSignedUrl(cfg: SignerGetSignedUrlConfig): Promise<SignerGetSignedUrlResponse>;
|
||||
private getSignedUrlV2;
|
||||
private getSignedUrlV4;
|
||||
/**
|
||||
* Create canonical headers for signing v4 url.
|
||||
*
|
||||
* The canonical headers for v4-signing a request demands header names are
|
||||
* first lowercased, followed by sorting the header names.
|
||||
* Then, construct the canonical headers part of the request:
|
||||
* <lowercasedHeaderName> + ":" + Trim(<value>) + "\n"
|
||||
* ..
|
||||
* <lowercasedHeaderName> + ":" + Trim(<value>) + "\n"
|
||||
*
|
||||
* @param headers
|
||||
* @private
|
||||
*/
|
||||
getCanonicalHeaders(headers: http.OutgoingHttpHeaders): string;
|
||||
getCanonicalRequest(method: string, path: string, query: string, headers: string, signedHeaders: string, contentSha256?: string): string;
|
||||
getCanonicalQueryParams(query: Query): string;
|
||||
getResourcePath(cname: boolean, bucket: string, file?: string): string;
|
||||
parseExpires(expires: string | number | Date, current?: Date): number;
|
||||
parseAccessibleAt(accessibleAt?: string | number | Date): number;
|
||||
}
|
||||
/**
|
||||
* Custom error type for errors related to getting signed errors and policies.
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
export declare class SigningError extends Error {
|
||||
name: string;
|
||||
}
|
||||
export {};
|
||||
@ -0,0 +1,290 @@
|
||||
"use strict";
|
||||
// Copyright 2020 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.SigningError = exports.URLSigner = exports.PATH_STYLED_HOST = exports.SignerExceptionMessages = void 0;
|
||||
const crypto = require("crypto");
|
||||
const url = require("url");
|
||||
const storage_1 = require("./storage");
|
||||
const util_1 = require("./util");
|
||||
var SignerExceptionMessages;
|
||||
(function (SignerExceptionMessages) {
|
||||
SignerExceptionMessages["ACCESSIBLE_DATE_INVALID"] = "The accessible at date provided was invalid.";
|
||||
SignerExceptionMessages["EXPIRATION_BEFORE_ACCESSIBLE_DATE"] = "An expiration date cannot be before accessible date.";
|
||||
SignerExceptionMessages["X_GOOG_CONTENT_SHA256"] = "The header X-Goog-Content-SHA256 must be a hexadecimal string.";
|
||||
})(SignerExceptionMessages = exports.SignerExceptionMessages || (exports.SignerExceptionMessages = {}));
|
||||
/*
|
||||
* Default signing version for getSignedUrl is 'v2'.
|
||||
*/
|
||||
const DEFAULT_SIGNING_VERSION = 'v2';
|
||||
const SEVEN_DAYS = 7 * 24 * 60 * 60;
|
||||
/**
|
||||
* @const {string}
|
||||
* @private
|
||||
*/
|
||||
exports.PATH_STYLED_HOST = 'https://storage.googleapis.com';
|
||||
class URLSigner {
|
||||
constructor(authClient, bucket, file) {
|
||||
this.bucket = bucket;
|
||||
this.file = file;
|
||||
this.authClient = authClient;
|
||||
}
|
||||
getSignedUrl(cfg) {
|
||||
const expiresInSeconds = this.parseExpires(cfg.expires);
|
||||
const method = cfg.method;
|
||||
const accessibleAtInSeconds = this.parseAccessibleAt(cfg.accessibleAt);
|
||||
if (expiresInSeconds < accessibleAtInSeconds) {
|
||||
throw new Error(SignerExceptionMessages.EXPIRATION_BEFORE_ACCESSIBLE_DATE);
|
||||
}
|
||||
let customHost;
|
||||
// Default style is `path`.
|
||||
const isVirtualHostedStyle = cfg.virtualHostedStyle || false;
|
||||
if (cfg.cname) {
|
||||
customHost = cfg.cname;
|
||||
}
|
||||
else if (isVirtualHostedStyle) {
|
||||
customHost = `https://${this.bucket.name}.storage.googleapis.com`;
|
||||
}
|
||||
const secondsToMilliseconds = 1000;
|
||||
const config = Object.assign({}, cfg, {
|
||||
method,
|
||||
expiration: expiresInSeconds,
|
||||
accessibleAt: new Date(secondsToMilliseconds * accessibleAtInSeconds),
|
||||
bucket: this.bucket.name,
|
||||
file: this.file ? (0, util_1.encodeURI)(this.file.name, false) : undefined,
|
||||
});
|
||||
if (customHost) {
|
||||
config.cname = customHost;
|
||||
}
|
||||
const version = cfg.version || DEFAULT_SIGNING_VERSION;
|
||||
let promise;
|
||||
if (version === 'v2') {
|
||||
promise = this.getSignedUrlV2(config);
|
||||
}
|
||||
else if (version === 'v4') {
|
||||
promise = this.getSignedUrlV4(config);
|
||||
}
|
||||
else {
|
||||
throw new Error(`Invalid signed URL version: ${version}. Supported versions are 'v2' and 'v4'.`);
|
||||
}
|
||||
return promise.then(query => {
|
||||
query = Object.assign(query, cfg.queryParams);
|
||||
const signedUrl = new url.URL(config.cname || exports.PATH_STYLED_HOST);
|
||||
signedUrl.pathname = this.getResourcePath(!!config.cname, this.bucket.name, config.file);
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
signedUrl.search = (0, util_1.qsStringify)(query);
|
||||
return signedUrl.href;
|
||||
});
|
||||
}
|
||||
getSignedUrlV2(config) {
|
||||
const canonicalHeadersString = this.getCanonicalHeaders(config.extensionHeaders || {});
|
||||
const resourcePath = this.getResourcePath(false, config.bucket, config.file);
|
||||
const blobToSign = [
|
||||
config.method,
|
||||
config.contentMd5 || '',
|
||||
config.contentType || '',
|
||||
config.expiration,
|
||||
canonicalHeadersString + resourcePath,
|
||||
].join('\n');
|
||||
const sign = async () => {
|
||||
const authClient = this.authClient;
|
||||
try {
|
||||
const signature = await authClient.sign(blobToSign);
|
||||
const credentials = await authClient.getCredentials();
|
||||
return {
|
||||
GoogleAccessId: credentials.client_email,
|
||||
Expires: config.expiration,
|
||||
Signature: signature,
|
||||
};
|
||||
}
|
||||
catch (err) {
|
||||
const error = err;
|
||||
const signingErr = new SigningError(error.message);
|
||||
signingErr.stack = error.stack;
|
||||
throw signingErr;
|
||||
}
|
||||
};
|
||||
return sign();
|
||||
}
|
||||
getSignedUrlV4(config) {
|
||||
config.accessibleAt = config.accessibleAt
|
||||
? config.accessibleAt
|
||||
: new Date();
|
||||
const millisecondsToSeconds = 1.0 / 1000.0;
|
||||
const expiresPeriodInSeconds = config.expiration - config.accessibleAt.valueOf() * millisecondsToSeconds;
|
||||
// v4 limit expiration to be 7 days maximum
|
||||
if (expiresPeriodInSeconds > SEVEN_DAYS) {
|
||||
throw new Error(`Max allowed expiration is seven days (${SEVEN_DAYS} seconds).`);
|
||||
}
|
||||
const extensionHeaders = Object.assign({}, config.extensionHeaders);
|
||||
const fqdn = new url.URL(config.cname || exports.PATH_STYLED_HOST);
|
||||
extensionHeaders.host = fqdn.host;
|
||||
if (config.contentMd5) {
|
||||
extensionHeaders['content-md5'] = config.contentMd5;
|
||||
}
|
||||
if (config.contentType) {
|
||||
extensionHeaders['content-type'] = config.contentType;
|
||||
}
|
||||
let contentSha256;
|
||||
const sha256Header = extensionHeaders['x-goog-content-sha256'];
|
||||
if (sha256Header) {
|
||||
if (typeof sha256Header !== 'string' ||
|
||||
!/[A-Fa-f0-9]{40}/.test(sha256Header)) {
|
||||
throw new Error(SignerExceptionMessages.X_GOOG_CONTENT_SHA256);
|
||||
}
|
||||
contentSha256 = sha256Header;
|
||||
}
|
||||
const signedHeaders = Object.keys(extensionHeaders)
|
||||
.map(header => header.toLowerCase())
|
||||
.sort()
|
||||
.join(';');
|
||||
const extensionHeadersString = this.getCanonicalHeaders(extensionHeaders);
|
||||
const datestamp = (0, util_1.formatAsUTCISO)(config.accessibleAt);
|
||||
const credentialScope = `${datestamp}/auto/storage/goog4_request`;
|
||||
const sign = async () => {
|
||||
const credentials = await this.authClient.getCredentials();
|
||||
const credential = `${credentials.client_email}/${credentialScope}`;
|
||||
const dateISO = (0, util_1.formatAsUTCISO)(config.accessibleAt ? config.accessibleAt : new Date(), true);
|
||||
const queryParams = {
|
||||
'X-Goog-Algorithm': 'GOOG4-RSA-SHA256',
|
||||
'X-Goog-Credential': credential,
|
||||
'X-Goog-Date': dateISO,
|
||||
'X-Goog-Expires': expiresPeriodInSeconds.toString(10),
|
||||
'X-Goog-SignedHeaders': signedHeaders,
|
||||
...(config.queryParams || {}),
|
||||
};
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
const canonicalQueryParams = this.getCanonicalQueryParams(queryParams);
|
||||
const canonicalRequest = this.getCanonicalRequest(config.method, this.getResourcePath(!!config.cname, config.bucket, config.file), canonicalQueryParams, extensionHeadersString, signedHeaders, contentSha256);
|
||||
const hash = crypto
|
||||
.createHash('sha256')
|
||||
.update(canonicalRequest)
|
||||
.digest('hex');
|
||||
const blobToSign = [
|
||||
'GOOG4-RSA-SHA256',
|
||||
dateISO,
|
||||
credentialScope,
|
||||
hash,
|
||||
].join('\n');
|
||||
try {
|
||||
const signature = await this.authClient.sign(blobToSign);
|
||||
const signatureHex = Buffer.from(signature, 'base64').toString('hex');
|
||||
const signedQuery = Object.assign({}, queryParams, {
|
||||
'X-Goog-Signature': signatureHex,
|
||||
});
|
||||
return signedQuery;
|
||||
}
|
||||
catch (err) {
|
||||
const error = err;
|
||||
const signingErr = new SigningError(error.message);
|
||||
signingErr.stack = error.stack;
|
||||
throw signingErr;
|
||||
}
|
||||
};
|
||||
return sign();
|
||||
}
|
||||
/**
|
||||
* Create canonical headers for signing v4 url.
|
||||
*
|
||||
* The canonical headers for v4-signing a request demands header names are
|
||||
* first lowercased, followed by sorting the header names.
|
||||
* Then, construct the canonical headers part of the request:
|
||||
* <lowercasedHeaderName> + ":" + Trim(<value>) + "\n"
|
||||
* ..
|
||||
* <lowercasedHeaderName> + ":" + Trim(<value>) + "\n"
|
||||
*
|
||||
* @param headers
|
||||
* @private
|
||||
*/
|
||||
getCanonicalHeaders(headers) {
|
||||
// Sort headers by their lowercased names
|
||||
const sortedHeaders = (0, util_1.objectEntries)(headers)
|
||||
// Convert header names to lowercase
|
||||
.map(([headerName, value]) => [
|
||||
headerName.toLowerCase(),
|
||||
value,
|
||||
])
|
||||
.sort((a, b) => a[0].localeCompare(b[0]));
|
||||
return sortedHeaders
|
||||
.filter(([, value]) => value !== undefined)
|
||||
.map(([headerName, value]) => {
|
||||
// - Convert Array (multi-valued header) into string, delimited by
|
||||
// ',' (no space).
|
||||
// - Trim leading and trailing spaces.
|
||||
// - Convert sequential (2+) spaces into a single space
|
||||
const canonicalValue = `${value}`.trim().replace(/\s{2,}/g, ' ');
|
||||
return `${headerName}:${canonicalValue}\n`;
|
||||
})
|
||||
.join('');
|
||||
}
|
||||
getCanonicalRequest(method, path, query, headers, signedHeaders, contentSha256) {
|
||||
return [
|
||||
method,
|
||||
path,
|
||||
query,
|
||||
headers,
|
||||
signedHeaders,
|
||||
contentSha256 || 'UNSIGNED-PAYLOAD',
|
||||
].join('\n');
|
||||
}
|
||||
getCanonicalQueryParams(query) {
|
||||
return (0, util_1.objectEntries)(query)
|
||||
.map(([key, value]) => [(0, util_1.encodeURI)(key, true), (0, util_1.encodeURI)(value, true)])
|
||||
.sort((a, b) => (a[0] < b[0] ? -1 : 1))
|
||||
.map(([key, value]) => `${key}=${value}`)
|
||||
.join('&');
|
||||
}
|
||||
getResourcePath(cname, bucket, file) {
|
||||
if (cname) {
|
||||
return '/' + (file || '');
|
||||
}
|
||||
else if (file) {
|
||||
return `/${bucket}/${file}`;
|
||||
}
|
||||
else {
|
||||
return `/${bucket}`;
|
||||
}
|
||||
}
|
||||
parseExpires(expires, current = new Date()) {
|
||||
const expiresInMSeconds = new Date(expires).valueOf();
|
||||
if (isNaN(expiresInMSeconds)) {
|
||||
throw new Error(storage_1.ExceptionMessages.EXPIRATION_DATE_INVALID);
|
||||
}
|
||||
if (expiresInMSeconds < current.valueOf()) {
|
||||
throw new Error(storage_1.ExceptionMessages.EXPIRATION_DATE_PAST);
|
||||
}
|
||||
return Math.floor(expiresInMSeconds / 1000); // The API expects seconds.
|
||||
}
|
||||
parseAccessibleAt(accessibleAt) {
|
||||
const accessibleAtInMSeconds = new Date(accessibleAt || new Date()).valueOf();
|
||||
if (isNaN(accessibleAtInMSeconds)) {
|
||||
throw new Error(SignerExceptionMessages.ACCESSIBLE_DATE_INVALID);
|
||||
}
|
||||
return Math.floor(accessibleAtInMSeconds / 1000); // The API expects seconds.
|
||||
}
|
||||
}
|
||||
exports.URLSigner = URLSigner;
|
||||
/**
|
||||
* Custom error type for errors related to getting signed errors and policies.
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
class SigningError extends Error {
|
||||
constructor() {
|
||||
super(...arguments);
|
||||
this.name = 'SigningError';
|
||||
}
|
||||
}
|
||||
exports.SigningError = SigningError;
|
||||
//# sourceMappingURL=signer.js.map
|
||||
@ -0,0 +1,721 @@
|
||||
/// <reference types="node" />
|
||||
import { ApiError, Metadata, Service, ServiceOptions } from './nodejs-common';
|
||||
import { Readable } from 'stream';
|
||||
import { Bucket } from './bucket';
|
||||
import { Channel } from './channel';
|
||||
import { File } from './file';
|
||||
import { HmacKey, HmacKeyMetadata, HmacKeyOptions } from './hmacKey';
|
||||
import { CRC32CValidatorGenerator } from './crc32c';
|
||||
export interface GetServiceAccountOptions {
|
||||
userProject?: string;
|
||||
}
|
||||
export interface ServiceAccount {
|
||||
emailAddress?: string;
|
||||
}
|
||||
export type GetServiceAccountResponse = [ServiceAccount, Metadata];
|
||||
export interface GetServiceAccountCallback {
|
||||
(err: Error | null, serviceAccount?: ServiceAccount, apiResponse?: Metadata): void;
|
||||
}
|
||||
export interface CreateBucketQuery {
|
||||
project: string;
|
||||
userProject: string;
|
||||
}
|
||||
export declare enum IdempotencyStrategy {
|
||||
RetryAlways = 0,
|
||||
RetryConditional = 1,
|
||||
RetryNever = 2
|
||||
}
|
||||
export interface RetryOptions {
|
||||
retryDelayMultiplier?: number;
|
||||
totalTimeout?: number;
|
||||
maxRetryDelay?: number;
|
||||
autoRetry?: boolean;
|
||||
maxRetries?: number;
|
||||
retryableErrorFn?: (err: ApiError) => boolean;
|
||||
idempotencyStrategy?: IdempotencyStrategy;
|
||||
}
|
||||
export interface PreconditionOptions {
|
||||
ifGenerationMatch?: number;
|
||||
ifGenerationNotMatch?: number;
|
||||
ifMetagenerationMatch?: number;
|
||||
ifMetagenerationNotMatch?: number;
|
||||
}
|
||||
export interface StorageOptions extends ServiceOptions {
|
||||
/**
|
||||
* The API endpoint of the service used to make requests.
|
||||
* Defaults to `storage.googleapis.com`.
|
||||
*/
|
||||
apiEndpoint?: string;
|
||||
crc32cGenerator?: CRC32CValidatorGenerator;
|
||||
retryOptions?: RetryOptions;
|
||||
}
|
||||
export interface BucketOptions {
|
||||
crc32cGenerator?: CRC32CValidatorGenerator;
|
||||
kmsKeyName?: string;
|
||||
preconditionOpts?: PreconditionOptions;
|
||||
userProject?: string;
|
||||
}
|
||||
export interface Cors {
|
||||
maxAgeSeconds?: number;
|
||||
method?: string[];
|
||||
origin?: string[];
|
||||
responseHeader?: string[];
|
||||
}
|
||||
interface Versioning {
|
||||
enabled: boolean;
|
||||
}
|
||||
/**
|
||||
* Custom placement configuration.
|
||||
* Initially used for dual-region buckets.
|
||||
**/
|
||||
export interface CustomPlacementConfig {
|
||||
dataLocations?: string[];
|
||||
}
|
||||
export interface AutoclassConfig {
|
||||
enabled?: boolean;
|
||||
}
|
||||
export interface CreateBucketRequest {
|
||||
archive?: boolean;
|
||||
autoclass?: AutoclassConfig;
|
||||
coldline?: boolean;
|
||||
cors?: Cors[];
|
||||
customPlacementConfig?: CustomPlacementConfig;
|
||||
dra?: boolean;
|
||||
location?: string;
|
||||
multiRegional?: boolean;
|
||||
nearline?: boolean;
|
||||
regional?: boolean;
|
||||
requesterPays?: boolean;
|
||||
retentionPolicy?: object;
|
||||
rpo?: string;
|
||||
standard?: boolean;
|
||||
storageClass?: string;
|
||||
userProject?: string;
|
||||
versioning?: Versioning;
|
||||
}
|
||||
export type CreateBucketResponse = [Bucket, Metadata];
|
||||
export interface BucketCallback {
|
||||
(err: Error | null, bucket?: Bucket | null, apiResponse?: Metadata): void;
|
||||
}
|
||||
export type GetBucketsResponse = [Bucket[], {}, Metadata];
|
||||
export interface GetBucketsCallback {
|
||||
(err: Error | null, buckets: Bucket[], nextQuery?: {}, apiResponse?: Metadata): void;
|
||||
}
|
||||
export interface GetBucketsRequest {
|
||||
prefix?: string;
|
||||
project?: string;
|
||||
autoPaginate?: boolean;
|
||||
maxApiCalls?: number;
|
||||
maxResults?: number;
|
||||
pageToken?: string;
|
||||
userProject?: string;
|
||||
}
|
||||
export interface HmacKeyResourceResponse {
|
||||
metadata: HmacKeyMetadata;
|
||||
secret: string;
|
||||
}
|
||||
export type CreateHmacKeyResponse = [HmacKey, string, HmacKeyResourceResponse];
|
||||
export interface CreateHmacKeyOptions {
|
||||
projectId?: string;
|
||||
userProject?: string;
|
||||
}
|
||||
export interface CreateHmacKeyCallback {
|
||||
(err: Error | null, hmacKey?: HmacKey | null, secret?: string | null, apiResponse?: HmacKeyResourceResponse): void;
|
||||
}
|
||||
export interface GetHmacKeysOptions {
|
||||
projectId?: string;
|
||||
serviceAccountEmail?: string;
|
||||
showDeletedKeys?: boolean;
|
||||
autoPaginate?: boolean;
|
||||
maxApiCalls?: number;
|
||||
maxResults?: number;
|
||||
pageToken?: string;
|
||||
userProject?: string;
|
||||
}
|
||||
export interface GetHmacKeysCallback {
|
||||
(err: Error | null, hmacKeys: HmacKey[] | null, nextQuery?: {}, apiResponse?: Metadata): void;
|
||||
}
|
||||
export declare enum ExceptionMessages {
|
||||
EXPIRATION_DATE_INVALID = "The expiration date provided was invalid.",
|
||||
EXPIRATION_DATE_PAST = "An expiration date cannot be in the past.",
|
||||
INVALID_ACTION = "The action is not provided or invalid."
|
||||
}
|
||||
export declare enum StorageExceptionMessages {
|
||||
BUCKET_NAME_REQUIRED = "A bucket name is needed to use Cloud Storage.",
|
||||
BUCKET_NAME_REQUIRED_CREATE = "A name is required to create a bucket.",
|
||||
HMAC_SERVICE_ACCOUNT = "The first argument must be a service account email to create an HMAC key.",
|
||||
HMAC_ACCESS_ID = "An access ID is needed to create an HmacKey object."
|
||||
}
|
||||
export type GetHmacKeysResponse = [HmacKey[]];
|
||||
export declare const PROTOCOL_REGEX: RegExp;
|
||||
/**
|
||||
* Default behavior: Automatically retry retriable server errors.
|
||||
*
|
||||
* @const {boolean}
|
||||
*/
|
||||
export declare const AUTO_RETRY_DEFAULT = true;
|
||||
/**
|
||||
* Default behavior: Only attempt to retry retriable errors 3 times.
|
||||
*
|
||||
* @const {number}
|
||||
*/
|
||||
export declare const MAX_RETRY_DEFAULT = 3;
|
||||
/**
|
||||
* Default behavior: Wait twice as long as previous retry before retrying.
|
||||
*
|
||||
* @const {number}
|
||||
*/
|
||||
export declare const RETRY_DELAY_MULTIPLIER_DEFAULT = 2;
|
||||
/**
|
||||
* Default behavior: If the operation doesn't succeed after 600 seconds,
|
||||
* stop retrying.
|
||||
*
|
||||
* @const {number}
|
||||
*/
|
||||
export declare const TOTAL_TIMEOUT_DEFAULT = 600;
|
||||
/**
|
||||
* Default behavior: Wait no more than 64 seconds between retries.
|
||||
*
|
||||
* @const {number}
|
||||
*/
|
||||
export declare const MAX_RETRY_DELAY_DEFAULT = 64;
|
||||
/**
|
||||
* Returns true if the API request should be retried, given the error that was
|
||||
* given the first time the request was attempted.
|
||||
* @const
|
||||
* @param {error} err - The API error to check if it is appropriate to retry.
|
||||
* @return {boolean} True if the API request should be retried, false otherwise.
|
||||
*/
|
||||
export declare const RETRYABLE_ERR_FN_DEFAULT: (err?: ApiError) => boolean;
|
||||
/*! Developer Documentation
|
||||
*
|
||||
* Invoke this method to create a new Storage object bound with pre-determined
|
||||
* configuration options. For each object that can be created (e.g., a bucket),
|
||||
* there is an equivalent static and instance method. While they are classes,
|
||||
* they can be instantiated without use of the `new` keyword.
|
||||
*/
|
||||
/**
|
||||
* Cloud Storage uses access control lists (ACLs) to manage object and
|
||||
* bucket access. ACLs are the mechanism you use to share objects with other
|
||||
* users and allow other users to access your buckets and objects.
|
||||
*
|
||||
* This object provides constants to refer to the three permission levels that
|
||||
* can be granted to an entity:
|
||||
*
|
||||
* - `gcs.acl.OWNER_ROLE` - ("OWNER")
|
||||
* - `gcs.acl.READER_ROLE` - ("READER")
|
||||
* - `gcs.acl.WRITER_ROLE` - ("WRITER")
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/access-control/lists| About Access Control Lists}
|
||||
*
|
||||
* @name Storage#acl
|
||||
* @type {object}
|
||||
* @property {string} OWNER_ROLE
|
||||
* @property {string} READER_ROLE
|
||||
* @property {string} WRITER_ROLE
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const albums = storage.bucket('albums');
|
||||
*
|
||||
* //-
|
||||
* // Make all of the files currently in a bucket publicly readable.
|
||||
* //-
|
||||
* const options = {
|
||||
* entity: 'allUsers',
|
||||
* role: storage.acl.READER_ROLE
|
||||
* };
|
||||
*
|
||||
* albums.acl.add(options, function(err, aclObject) {});
|
||||
*
|
||||
* //-
|
||||
* // Make any new objects added to a bucket publicly readable.
|
||||
* //-
|
||||
* albums.acl.default.add(options, function(err, aclObject) {});
|
||||
*
|
||||
* //-
|
||||
* // Grant a user ownership permissions to a bucket.
|
||||
* //-
|
||||
* albums.acl.add({
|
||||
* entity: 'user-useremail@example.com',
|
||||
* role: storage.acl.OWNER_ROLE
|
||||
* }, function(err, aclObject) {});
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* albums.acl.add(options).then(function(data) {
|
||||
* const aclObject = data[0];
|
||||
* const apiResponse = data[1];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
/**
|
||||
* Get {@link Bucket} objects for all of the buckets in your project as
|
||||
* a readable object stream.
|
||||
*
|
||||
* @method Storage#getBucketsStream
|
||||
* @param {GetBucketsRequest} [query] Query object for listing buckets.
|
||||
* @returns {ReadableStream} A readable stream that emits {@link Bucket}
|
||||
* instances.
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* storage.getBucketsStream()
|
||||
* .on('error', console.error)
|
||||
* .on('data', function(bucket) {
|
||||
* // bucket is a Bucket object.
|
||||
* })
|
||||
* .on('end', function() {
|
||||
* // All buckets retrieved.
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If you anticipate many results, you can end a stream early to prevent
|
||||
* // unnecessary processing and API requests.
|
||||
* //-
|
||||
* storage.getBucketsStream()
|
||||
* .on('data', function(bucket) {
|
||||
* this.end();
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
/**
|
||||
* Get {@link HmacKey} objects for all of the HMAC keys in the project in a
|
||||
* readable object stream.
|
||||
*
|
||||
* @method Storage#getHmacKeysStream
|
||||
* @param {GetHmacKeysOptions} [options] Configuration options.
|
||||
* @returns {ReadableStream} A readable stream that emits {@link HmacKey}
|
||||
* instances.
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* storage.getHmacKeysStream()
|
||||
* .on('error', console.error)
|
||||
* .on('data', function(hmacKey) {
|
||||
* // hmacKey is an HmacKey object.
|
||||
* })
|
||||
* .on('end', function() {
|
||||
* // All HmacKey retrieved.
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // If you anticipate many results, you can end a stream early to prevent
|
||||
* // unnecessary processing and API requests.
|
||||
* //-
|
||||
* storage.getHmacKeysStream()
|
||||
* .on('data', function(bucket) {
|
||||
* this.end();
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
/**
|
||||
* <h4>ACLs</h4>
|
||||
* Cloud Storage uses access control lists (ACLs) to manage object and
|
||||
* bucket access. ACLs are the mechanism you use to share files with other users
|
||||
* and allow other users to access your buckets and files.
|
||||
*
|
||||
* To learn more about ACLs, read this overview on
|
||||
* {@link https://cloud.google.com/storage/docs/access-control| Access Control}.
|
||||
*
|
||||
* See {@link https://cloud.google.com/storage/docs/overview| Cloud Storage overview}
|
||||
* See {@link https://cloud.google.com/storage/docs/access-control| Access Control}
|
||||
*
|
||||
* @class
|
||||
*/
|
||||
export declare class Storage extends Service {
|
||||
/**
|
||||
* {@link Bucket} class.
|
||||
*
|
||||
* @name Storage.Bucket
|
||||
* @see Bucket
|
||||
* @type {Constructor}
|
||||
*/
|
||||
static Bucket: typeof Bucket;
|
||||
/**
|
||||
* {@link Channel} class.
|
||||
*
|
||||
* @name Storage.Channel
|
||||
* @see Channel
|
||||
* @type {Constructor}
|
||||
*/
|
||||
static Channel: typeof Channel;
|
||||
/**
|
||||
* {@link File} class.
|
||||
*
|
||||
* @name Storage.File
|
||||
* @see File
|
||||
* @type {Constructor}
|
||||
*/
|
||||
static File: typeof File;
|
||||
/**
|
||||
* {@link HmacKey} class.
|
||||
*
|
||||
* @name Storage.HmacKey
|
||||
* @see HmacKey
|
||||
* @type {Constructor}
|
||||
*/
|
||||
static HmacKey: typeof HmacKey;
|
||||
static acl: {
|
||||
OWNER_ROLE: string;
|
||||
READER_ROLE: string;
|
||||
WRITER_ROLE: string;
|
||||
};
|
||||
/**
|
||||
* Reference to {@link Storage.acl}.
|
||||
*
|
||||
* @name Storage#acl
|
||||
* @see Storage.acl
|
||||
*/
|
||||
acl: typeof Storage.acl;
|
||||
crc32cGenerator: CRC32CValidatorGenerator;
|
||||
getBucketsStream(): Readable;
|
||||
getHmacKeysStream(): Readable;
|
||||
retryOptions: RetryOptions;
|
||||
/**
|
||||
* @callback Crc32cGeneratorToStringCallback
|
||||
* A method returning the CRC32C as a base64-encoded string.
|
||||
*
|
||||
* @returns {string}
|
||||
*
|
||||
* @example
|
||||
* Hashing the string 'data' should return 'rth90Q=='
|
||||
*
|
||||
* ```js
|
||||
* const buffer = Buffer.from('data');
|
||||
* crc32c.update(buffer);
|
||||
* crc32c.toString(); // 'rth90Q=='
|
||||
* ```
|
||||
**/
|
||||
/**
|
||||
* @callback Crc32cGeneratorValidateCallback
|
||||
* A method validating a base64-encoded CRC32C string.
|
||||
*
|
||||
* @param {string} [value] base64-encoded CRC32C string to validate
|
||||
* @returns {boolean}
|
||||
*
|
||||
* @example
|
||||
* Should return `true` if the value matches, `false` otherwise
|
||||
*
|
||||
* ```js
|
||||
* const buffer = Buffer.from('data');
|
||||
* crc32c.update(buffer);
|
||||
* crc32c.validate('DkjKuA=='); // false
|
||||
* crc32c.validate('rth90Q=='); // true
|
||||
* ```
|
||||
**/
|
||||
/**
|
||||
* @callback Crc32cGeneratorUpdateCallback
|
||||
* A method for passing `Buffer`s for CRC32C generation.
|
||||
*
|
||||
* @param {Buffer} [data] data to update CRC32C value with
|
||||
* @returns {undefined}
|
||||
*
|
||||
* @example
|
||||
* Hashing buffers from 'some ' and 'text\n'
|
||||
*
|
||||
* ```js
|
||||
* const buffer1 = Buffer.from('some ');
|
||||
* crc32c.update(buffer1);
|
||||
*
|
||||
* const buffer2 = Buffer.from('text\n');
|
||||
* crc32c.update(buffer2);
|
||||
*
|
||||
* crc32c.toString(); // 'DkjKuA=='
|
||||
* ```
|
||||
**/
|
||||
/**
|
||||
* @typedef {object} CRC32CValidator
|
||||
* @property {Crc32cGeneratorToStringCallback}
|
||||
* @property {Crc32cGeneratorValidateCallback}
|
||||
* @property {Crc32cGeneratorUpdateCallback}
|
||||
*/
|
||||
/**
|
||||
* @callback Crc32cGeneratorCallback
|
||||
* @returns {CRC32CValidator}
|
||||
*/
|
||||
/**
|
||||
* @typedef {object} StorageOptions
|
||||
* @property {string} [projectId] The project ID from the Google Developer's
|
||||
* Console, e.g. 'grape-spaceship-123'. We will also check the environment
|
||||
* variable `GCLOUD_PROJECT` for your project ID. If your app is running
|
||||
* in an environment which supports {@link
|
||||
* https://cloud.google.com/docs/authentication/production#providing_credentials_to_your_application
|
||||
* Application Default Credentials}, your project ID will be detected
|
||||
* automatically.
|
||||
* @property {string} [keyFilename] Full path to the a .json, .pem, or .p12 key
|
||||
* downloaded from the Google Developers Console. If you provide a path to
|
||||
* a JSON file, the `projectId` option above is not necessary. NOTE: .pem and
|
||||
* .p12 require you to specify the `email` option as well.
|
||||
* @property {string} [email] Account email address. Required when using a .pem
|
||||
* or .p12 keyFilename.
|
||||
* @property {object} [credentials] Credentials object.
|
||||
* @property {string} [credentials.client_email]
|
||||
* @property {string} [credentials.private_key]
|
||||
* @property {object} [retryOptions] Options for customizing retries. Retriable server errors
|
||||
* will be retried with exponential delay between them dictated by the formula
|
||||
* max(maxRetryDelay, retryDelayMultiplier*retryNumber) until maxRetries or totalTimeout
|
||||
* has been reached. Retries will only happen if autoRetry is set to true.
|
||||
* @property {boolean} [retryOptions.autoRetry=true] Automatically retry requests if the
|
||||
* response is related to rate limits or certain intermittent server
|
||||
* errors. We will exponentially backoff subsequent requests by default.
|
||||
* @property {number} [retryOptions.retryDelayMultiplier = 2] the multiplier by which to
|
||||
* increase the delay time between the completion of failed requests, and the
|
||||
* initiation of the subsequent retrying request.
|
||||
* @property {number} [retryOptions.totalTimeout = 600] The total time, starting from
|
||||
* when the initial request is sent, after which an error will
|
||||
* be returned, regardless of the retrying attempts made meanwhile.
|
||||
* @property {number} [retryOptions.maxRetryDelay = 64] The maximum delay time between requests.
|
||||
* When this value is reached, ``retryDelayMultiplier`` will no longer be used to
|
||||
* increase delay time.
|
||||
* @property {number} [retryOptions.maxRetries=3] Maximum number of automatic retries
|
||||
* attempted before returning the error.
|
||||
* @property {function} [retryOptions.retryableErrorFn] Function that returns true if a given
|
||||
* error should be retried and false otherwise.
|
||||
* @property {enum} [retryOptions.idempotencyStrategy=IdempotencyStrategy.RetryConditional] Enumeration
|
||||
* controls how conditionally idempotent operations are retried. Possible values are: RetryAlways -
|
||||
* will respect other retry settings and attempt to retry conditionally idempotent operations. RetryConditional -
|
||||
* will retry conditionally idempotent operations if the correct preconditions are set. RetryNever - never
|
||||
* retry a conditionally idempotent operation.
|
||||
* @property {string} [userAgent] The value to be prepended to the User-Agent
|
||||
* header in API requests.
|
||||
* @property {object} [authClient] `AuthClient` or `GoogleAuth` client to reuse instead of creating a new one.
|
||||
* @property {number} [timeout] The amount of time in milliseconds to wait per http request before timing out.
|
||||
* @property {object[]} [interceptors_] Array of custom request interceptors to be returned in the order they were assigned.
|
||||
* @property {string} [apiEndpoint = storage.google.com] The API endpoint of the service used to make requests.
|
||||
* @property {boolean} [useAuthWithCustomEndpoint = false] Controls whether or not to use authentication when using a custom endpoint.
|
||||
* @property {Crc32cGeneratorCallback} [callback] A function that generates a CRC32C Validator. Defaults to {@link CRC32C}
|
||||
*/
|
||||
/**
|
||||
* Constructs the Storage client.
|
||||
*
|
||||
* @example
|
||||
* Create a client that uses Application Default Credentials
|
||||
* (ADC)
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* ```
|
||||
*
|
||||
* @example
|
||||
* Create a client with explicit credentials
|
||||
* ```
|
||||
* const storage = new Storage({
|
||||
* projectId: 'your-project-id',
|
||||
* keyFilename: '/path/to/keyfile.json'
|
||||
* });
|
||||
* ```
|
||||
*
|
||||
* @example
|
||||
* Create a client with credentials passed
|
||||
* by value as a JavaScript object
|
||||
* ```
|
||||
* const storage = new Storage({
|
||||
* projectId: 'your-project-id',
|
||||
* credentials: {
|
||||
* type: 'service_account',
|
||||
* project_id: 'xxxxxxx',
|
||||
* private_key_id: 'xxxx',
|
||||
* private_key:'-----BEGIN PRIVATE KEY-----xxxxxxx\n-----END PRIVATE KEY-----\n',
|
||||
* client_email: 'xxxx',
|
||||
* client_id: 'xxx',
|
||||
* auth_uri: 'https://accounts.google.com/o/oauth2/auth',
|
||||
* token_uri: 'https://oauth2.googleapis.com/token',
|
||||
* auth_provider_x509_cert_url: 'https://www.googleapis.com/oauth2/v1/certs',
|
||||
* client_x509_cert_url: 'xxx',
|
||||
* }
|
||||
* });
|
||||
* ```
|
||||
*
|
||||
* @example
|
||||
* Create a client with credentials passed
|
||||
* by loading a JSON file directly from disk
|
||||
* ```
|
||||
* const storage = new Storage({
|
||||
* projectId: 'your-project-id',
|
||||
* credentials: require('/path/to-keyfile.json')
|
||||
* });
|
||||
* ```
|
||||
*
|
||||
* @example
|
||||
* Create a client with an `AuthClient` (e.g. `DownscopedClient`)
|
||||
* ```
|
||||
* const {DownscopedClient} = require('google-auth-library');
|
||||
* const authClient = new DownscopedClient({...});
|
||||
*
|
||||
* const storage = new Storage({authClient});
|
||||
* ```
|
||||
*
|
||||
* Additional samples:
|
||||
* - https://github.com/googleapis/google-auth-library-nodejs#sample-usage-1
|
||||
* - https://github.com/googleapis/google-auth-library-nodejs/blob/main/samples/downscopedclient.js
|
||||
*
|
||||
* @param {StorageOptions} [options] Configuration options.
|
||||
*/
|
||||
constructor(options?: StorageOptions);
|
||||
private static sanitizeEndpoint;
|
||||
/**
|
||||
* Get a reference to a Cloud Storage bucket.
|
||||
*
|
||||
* @param {string} name Name of the bucket.
|
||||
* @param {object} [options] Configuration object.
|
||||
* @param {string} [options.kmsKeyName] A Cloud KMS key that will be used to
|
||||
* encrypt objects inserted into this bucket, if no encryption method is
|
||||
* specified.
|
||||
* @param {string} [options.userProject] User project to be billed for all
|
||||
* requests made from this Bucket object.
|
||||
* @returns {Bucket}
|
||||
* @see Bucket
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const albums = storage.bucket('albums');
|
||||
* const photos = storage.bucket('photos');
|
||||
* ```
|
||||
*/
|
||||
bucket(name: string, options?: BucketOptions): Bucket;
|
||||
/**
|
||||
* Reference a channel to receive notifications about changes to your bucket.
|
||||
*
|
||||
* @param {string} id The ID of the channel.
|
||||
* @param {string} resourceId The resource ID of the channel.
|
||||
* @returns {Channel}
|
||||
* @see Channel
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const channel = storage.channel('id', 'resource-id');
|
||||
* ```
|
||||
*/
|
||||
channel(id: string, resourceId: string): Channel;
|
||||
createBucket(name: string, metadata?: CreateBucketRequest): Promise<CreateBucketResponse>;
|
||||
createBucket(name: string, callback: BucketCallback): void;
|
||||
createBucket(name: string, metadata: CreateBucketRequest, callback: BucketCallback): void;
|
||||
createBucket(name: string, metadata: CreateBucketRequest, callback: BucketCallback): void;
|
||||
createHmacKey(serviceAccountEmail: string, options?: CreateHmacKeyOptions): Promise<CreateHmacKeyResponse>;
|
||||
createHmacKey(serviceAccountEmail: string, callback: CreateHmacKeyCallback): void;
|
||||
createHmacKey(serviceAccountEmail: string, options: CreateHmacKeyOptions, callback: CreateHmacKeyCallback): void;
|
||||
getBuckets(options?: GetBucketsRequest): Promise<GetBucketsResponse>;
|
||||
getBuckets(options: GetBucketsRequest, callback: GetBucketsCallback): void;
|
||||
getBuckets(callback: GetBucketsCallback): void;
|
||||
/**
|
||||
* Query object for listing HMAC keys.
|
||||
*
|
||||
* @typedef {object} GetHmacKeysOptions
|
||||
* @property {string} [projectId] The project ID of the project that owns
|
||||
* the service account of the requested HMAC key. If not provided,
|
||||
* the project ID used to instantiate the Storage client will be used.
|
||||
* @property {string} [serviceAccountEmail] If present, only HMAC keys for the
|
||||
* given service account are returned.
|
||||
* @property {boolean} [showDeletedKeys=false] If true, include keys in the DELETE
|
||||
* state. Default is false.
|
||||
* @property {boolean} [autoPaginate=true] Have pagination handled
|
||||
* automatically.
|
||||
* @property {number} [maxApiCalls] Maximum number of API calls to make.
|
||||
* @property {number} [maxResults] Maximum number of items plus prefixes to
|
||||
* return per call.
|
||||
* Note: By default will handle pagination automatically
|
||||
* if more than 1 page worth of results are requested per call.
|
||||
* When `autoPaginate` is set to `false` the smaller of `maxResults`
|
||||
* or 1 page of results will be returned per call.
|
||||
* @property {string} [pageToken] A previously-returned page token
|
||||
* representing part of the larger set of results to view.
|
||||
* @property {string} [userProject] This parameter is currently ignored.
|
||||
*/
|
||||
/**
|
||||
* @typedef {array} GetHmacKeysResponse
|
||||
* @property {HmacKey[]} 0 Array of {@link HmacKey} instances.
|
||||
* @param {object} nextQuery 1 A query object to receive more results.
|
||||
* @param {object} apiResponse 2 The full API response.
|
||||
*/
|
||||
/**
|
||||
* @callback GetHmacKeysCallback
|
||||
* @param {?Error} err Request error, if any.
|
||||
* @param {HmacKey[]} hmacKeys Array of {@link HmacKey} instances.
|
||||
* @param {object} nextQuery A query object to receive more results.
|
||||
* @param {object} apiResponse The full API response.
|
||||
*/
|
||||
/**
|
||||
* Retrieves a list of HMAC keys matching the criteria.
|
||||
*
|
||||
* The authenticated user must have storage.hmacKeys.list permission for the project in which the key exists.
|
||||
*
|
||||
* @param {GetHmacKeysOption} options Configuration options.
|
||||
* @param {GetHmacKeysCallback} callback Callback function.
|
||||
* @return {Promise<GetHmacKeysResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* storage.getHmacKeys(function(err, hmacKeys) {
|
||||
* if (!err) {
|
||||
* // hmacKeys is an array of HmacKey objects.
|
||||
* }
|
||||
* });
|
||||
*
|
||||
* //-
|
||||
* // To control how many API requests are made and page through the results
|
||||
* // manually, set `autoPaginate` to `false`.
|
||||
* //-
|
||||
* const callback = function(err, hmacKeys, nextQuery, apiResponse) {
|
||||
* if (nextQuery) {
|
||||
* // More results exist.
|
||||
* storage.getHmacKeys(nextQuery, callback);
|
||||
* }
|
||||
*
|
||||
* // The `metadata` property is populated for you with the metadata at the
|
||||
* // time of fetching.
|
||||
* hmacKeys[0].metadata;
|
||||
* };
|
||||
*
|
||||
* storage.getHmacKeys({
|
||||
* autoPaginate: false
|
||||
* }, callback);
|
||||
*
|
||||
* //-
|
||||
* // If the callback is omitted, we'll return a Promise.
|
||||
* //-
|
||||
* storage.getHmacKeys().then(function(data) {
|
||||
* const hmacKeys = data[0];
|
||||
* });
|
||||
* ```
|
||||
*/
|
||||
getHmacKeys(options?: GetHmacKeysOptions): Promise<GetHmacKeysResponse>;
|
||||
getHmacKeys(callback: GetHmacKeysCallback): void;
|
||||
getHmacKeys(options: GetHmacKeysOptions, callback: GetHmacKeysCallback): void;
|
||||
getServiceAccount(options?: GetServiceAccountOptions): Promise<GetServiceAccountResponse>;
|
||||
getServiceAccount(options?: GetServiceAccountOptions): Promise<GetServiceAccountResponse>;
|
||||
getServiceAccount(options: GetServiceAccountOptions, callback: GetServiceAccountCallback): void;
|
||||
getServiceAccount(callback: GetServiceAccountCallback): void;
|
||||
/**
|
||||
* Get a reference to an HmacKey object.
|
||||
* Note: this does not fetch the HMAC key's metadata. Use HmacKey#get() to
|
||||
* retrieve and populate the metadata.
|
||||
*
|
||||
* To get a reference to an HMAC key that's not created for a service
|
||||
* account in the same project used to instantiate the Storage client,
|
||||
* supply the project's ID as `projectId` in the `options` argument.
|
||||
*
|
||||
* @param {string} accessId The HMAC key's access ID.
|
||||
* @param {HmacKeyOptions} options HmacKey constructor options.
|
||||
* @returns {HmacKey}
|
||||
* @see HmacKey
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const hmacKey = storage.hmacKey('ACCESS_ID');
|
||||
* ```
|
||||
*/
|
||||
hmacKey(accessId: string, options?: HmacKeyOptions): HmacKey;
|
||||
}
|
||||
export {};
|
||||
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,166 @@
|
||||
/*!
|
||||
* Copyright 2022 Google LLC. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
import { Bucket, UploadOptions, UploadResponse } from './bucket';
|
||||
import { DownloadOptions, DownloadResponse, File } from './file';
|
||||
export interface UploadManyFilesOptions {
|
||||
concurrencyLimit?: number;
|
||||
skipIfExists?: boolean;
|
||||
prefix?: string;
|
||||
passthroughOptions?: Omit<UploadOptions, 'destination'>;
|
||||
}
|
||||
export interface DownloadManyFilesOptions {
|
||||
concurrencyLimit?: number;
|
||||
prefix?: string;
|
||||
stripPrefix?: string;
|
||||
passthroughOptions?: DownloadOptions;
|
||||
}
|
||||
export interface DownloadFileInChunksOptions {
|
||||
concurrencyLimit?: number;
|
||||
chunkSizeBytes?: number;
|
||||
destination?: string;
|
||||
validation?: 'crc32c' | false;
|
||||
}
|
||||
/**
|
||||
* Create a TransferManager object to perform parallel transfer operations on a Cloud Storage bucket.
|
||||
*
|
||||
* @class
|
||||
* @hideconstructor
|
||||
*
|
||||
* @param {Bucket} bucket A {@link Bucket} instance
|
||||
* @experimental
|
||||
*/
|
||||
export declare class TransferManager {
|
||||
bucket: Bucket;
|
||||
constructor(bucket: Bucket);
|
||||
/**
|
||||
* @typedef {object} UploadManyFilesOptions
|
||||
* @property {number} [concurrencyLimit] The number of concurrently executing promises
|
||||
* to use when uploading the files.
|
||||
* @property {boolean} [skipIfExists] Do not upload the file if it already exists in
|
||||
* the bucket. This will set the precondition ifGenerationMatch = 0.
|
||||
* @property {string} [prefix] A prefix to append to all of the uploaded files.
|
||||
* @property {object} [passthroughOptions] {@link UploadOptions} Options to be passed through
|
||||
* to each individual upload operation.
|
||||
* @experimental
|
||||
*/
|
||||
/**
|
||||
* Upload multiple files in parallel to the bucket. This is a convenience method
|
||||
* that utilizes {@link Bucket#upload} to perform the upload.
|
||||
*
|
||||
* @param {array | string} [filePathsOrDirectory] An array of fully qualified paths to the files or a directory name.
|
||||
* If a directory name is provided, the directory will be recursively walked and all files will be added to the upload list.
|
||||
* to be uploaded to the bucket
|
||||
* @param {UploadManyFilesOptions} [options] Configuration options.
|
||||
* @returns {Promise<UploadResponse[]>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
* const transferManager = new TransferManager(bucket);
|
||||
*
|
||||
* //-
|
||||
* // Upload multiple files in parallel.
|
||||
* //-
|
||||
* const response = await transferManager.uploadManyFiles(['/local/path/file1.txt, 'local/path/file2.txt']);
|
||||
* // Your bucket now contains:
|
||||
* // - "local/path/file1.txt" (with the contents of '/local/path/file1.txt')
|
||||
* // - "local/path/file2.txt" (with the contents of '/local/path/file2.txt')
|
||||
* const response = await transferManager.uploadManyFiles('/local/directory');
|
||||
* // Your bucket will now contain all files contained in '/local/directory' maintaining the subdirectory structure.
|
||||
* ```
|
||||
* @experimental
|
||||
*/
|
||||
uploadManyFiles(filePathsOrDirectory: string[] | string, options?: UploadManyFilesOptions): Promise<UploadResponse[]>;
|
||||
/**
|
||||
* @typedef {object} DownloadManyFilesOptions
|
||||
* @property {number} [concurrencyLimit] The number of concurrently executing promises
|
||||
* to use when downloading the files.
|
||||
* @property {string} [prefix] A prefix to append to all of the downloaded files.
|
||||
* @property {string} [stripPrefix] A prefix to remove from all of the downloaded files.
|
||||
* @property {object} [passthroughOptions] {@link DownloadOptions} Options to be passed through
|
||||
* to each individual download operation.
|
||||
* @experimental
|
||||
*/
|
||||
/**
|
||||
* Download multiple files in parallel to the local filesystem. This is a convenience method
|
||||
* that utilizes {@link File#download} to perform the download.
|
||||
*
|
||||
* @param {array | string} [filesOrFolder] An array of file name strings or file objects to be downloaded. If
|
||||
* a string is provided this will be treated as a GCS prefix and all files with that prefix will be downloaded.
|
||||
* @param {DownloadManyFilesOptions} [options] Configuration options.
|
||||
* @returns {Promise<DownloadResponse[]>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
* const transferManager = new TransferManager(bucket);
|
||||
*
|
||||
* //-
|
||||
* // Download multiple files in parallel.
|
||||
* //-
|
||||
* const response = await transferManager.downloadManyFiles(['file1.txt', 'file2.txt']);
|
||||
* // The following files have been downloaded:
|
||||
* // - "file1.txt" (with the contents from my-bucket.file1.txt)
|
||||
* // - "file2.txt" (with the contents from my-bucket.file2.txt)
|
||||
* const response = await transferManager.downloadManyFiles([bucket.File('file1.txt'), bucket.File('file2.txt')]);
|
||||
* // The following files have been downloaded:
|
||||
* // - "file1.txt" (with the contents from my-bucket.file1.txt)
|
||||
* // - "file2.txt" (with the contents from my-bucket.file2.txt)
|
||||
* const response = await transferManager.downloadManyFiles('test-folder');
|
||||
* // All files with GCS prefix of 'test-folder' have been downloaded.
|
||||
* ```
|
||||
* @experimental
|
||||
*/
|
||||
downloadManyFiles(filesOrFolder: File[] | string[] | string, options?: DownloadManyFilesOptions): Promise<void | DownloadResponse[]>;
|
||||
/**
|
||||
* @typedef {object} DownloadFileInChunksOptions
|
||||
* @property {number} [concurrencyLimit] The number of concurrently executing promises
|
||||
* to use when downloading the file.
|
||||
* @property {number} [chunkSizeBytes] The size in bytes of each chunk to be downloaded.
|
||||
* @property {string | boolean} [validation] Whether or not to perform a CRC32C validation check when download is complete.
|
||||
* @experimental
|
||||
*/
|
||||
/**
|
||||
* Download a large file in chunks utilizing parallel download operations. This is a convenience method
|
||||
* that utilizes {@link File#download} to perform the download.
|
||||
*
|
||||
* @param {object} [file | string] {@link File} to download.
|
||||
* @param {DownloadFileInChunksOptions} [options] Configuration options.
|
||||
* @returns {Promise<DownloadResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
* const transferManager = new TransferManager(bucket);
|
||||
*
|
||||
* //-
|
||||
* // Download a large file in chunks utilizing parallel operations.
|
||||
* //-
|
||||
* const response = await transferManager.downloadLargeFile(bucket.file('large-file.txt');
|
||||
* // Your local directory now contains:
|
||||
* // - "large-file.txt" (with the contents from my-bucket.large-file.txt)
|
||||
* ```
|
||||
* @experimental
|
||||
*/
|
||||
downloadFileInChunks(fileOrName: File | string, options?: DownloadFileInChunksOptions): Promise<void | DownloadResponse>;
|
||||
private getPathsFromDirectory;
|
||||
}
|
||||
@ -0,0 +1,309 @@
|
||||
"use strict";
|
||||
/*!
|
||||
* Copyright 2022 Google LLC. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.TransferManager = void 0;
|
||||
const pLimit = require("p-limit");
|
||||
const path = require("path");
|
||||
const extend = require("extend");
|
||||
const fs_1 = require("fs");
|
||||
const crc32c_1 = require("./crc32c");
|
||||
/**
|
||||
* Default number of concurrently executing promises to use when calling uploadManyFiles.
|
||||
* @experimental
|
||||
*/
|
||||
const DEFAULT_PARALLEL_UPLOAD_LIMIT = 2;
|
||||
/**
|
||||
* Default number of concurrently executing promises to use when calling downloadManyFiles.
|
||||
* @experimental
|
||||
*/
|
||||
const DEFAULT_PARALLEL_DOWNLOAD_LIMIT = 2;
|
||||
/**
|
||||
* Default number of concurrently executing promises to use when calling downloadFileInChunks.
|
||||
* @experimental
|
||||
*/
|
||||
const DEFAULT_PARALLEL_CHUNKED_DOWNLOAD_LIMIT = 2;
|
||||
/**
|
||||
* The minimum size threshold in bytes at which to apply a chunked download strategy when calling downloadFileInChunks.
|
||||
* @experimental
|
||||
*/
|
||||
const DOWNLOAD_IN_CHUNKS_FILE_SIZE_THRESHOLD = 32 * 1024 * 1024;
|
||||
/**
|
||||
* The chunk size in bytes to use when calling downloadFileInChunks.
|
||||
* @experimental
|
||||
*/
|
||||
const DOWNLOAD_IN_CHUNKS_DEFAULT_CHUNK_SIZE = 10 * 1024 * 1024;
|
||||
const EMPTY_REGEX = '(?:)';
|
||||
/**
|
||||
* Create a TransferManager object to perform parallel transfer operations on a Cloud Storage bucket.
|
||||
*
|
||||
* @class
|
||||
* @hideconstructor
|
||||
*
|
||||
* @param {Bucket} bucket A {@link Bucket} instance
|
||||
* @experimental
|
||||
*/
|
||||
class TransferManager {
|
||||
constructor(bucket) {
|
||||
this.bucket = bucket;
|
||||
}
|
||||
/**
|
||||
* @typedef {object} UploadManyFilesOptions
|
||||
* @property {number} [concurrencyLimit] The number of concurrently executing promises
|
||||
* to use when uploading the files.
|
||||
* @property {boolean} [skipIfExists] Do not upload the file if it already exists in
|
||||
* the bucket. This will set the precondition ifGenerationMatch = 0.
|
||||
* @property {string} [prefix] A prefix to append to all of the uploaded files.
|
||||
* @property {object} [passthroughOptions] {@link UploadOptions} Options to be passed through
|
||||
* to each individual upload operation.
|
||||
* @experimental
|
||||
*/
|
||||
/**
|
||||
* Upload multiple files in parallel to the bucket. This is a convenience method
|
||||
* that utilizes {@link Bucket#upload} to perform the upload.
|
||||
*
|
||||
* @param {array | string} [filePathsOrDirectory] An array of fully qualified paths to the files or a directory name.
|
||||
* If a directory name is provided, the directory will be recursively walked and all files will be added to the upload list.
|
||||
* to be uploaded to the bucket
|
||||
* @param {UploadManyFilesOptions} [options] Configuration options.
|
||||
* @returns {Promise<UploadResponse[]>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
* const transferManager = new TransferManager(bucket);
|
||||
*
|
||||
* //-
|
||||
* // Upload multiple files in parallel.
|
||||
* //-
|
||||
* const response = await transferManager.uploadManyFiles(['/local/path/file1.txt, 'local/path/file2.txt']);
|
||||
* // Your bucket now contains:
|
||||
* // - "local/path/file1.txt" (with the contents of '/local/path/file1.txt')
|
||||
* // - "local/path/file2.txt" (with the contents of '/local/path/file2.txt')
|
||||
* const response = await transferManager.uploadManyFiles('/local/directory');
|
||||
* // Your bucket will now contain all files contained in '/local/directory' maintaining the subdirectory structure.
|
||||
* ```
|
||||
* @experimental
|
||||
*/
|
||||
async uploadManyFiles(filePathsOrDirectory, options = {}) {
|
||||
var _a;
|
||||
if (options.skipIfExists && ((_a = options.passthroughOptions) === null || _a === void 0 ? void 0 : _a.preconditionOpts)) {
|
||||
options.passthroughOptions.preconditionOpts.ifGenerationMatch = 0;
|
||||
}
|
||||
else if (options.skipIfExists &&
|
||||
options.passthroughOptions === undefined) {
|
||||
options.passthroughOptions = {
|
||||
preconditionOpts: {
|
||||
ifGenerationMatch: 0,
|
||||
},
|
||||
};
|
||||
}
|
||||
const limit = pLimit(options.concurrencyLimit || DEFAULT_PARALLEL_UPLOAD_LIMIT);
|
||||
const promises = [];
|
||||
let allPaths = [];
|
||||
if (!Array.isArray(filePathsOrDirectory)) {
|
||||
for await (const curPath of this.getPathsFromDirectory(filePathsOrDirectory)) {
|
||||
allPaths.push(curPath);
|
||||
}
|
||||
}
|
||||
else {
|
||||
allPaths = filePathsOrDirectory;
|
||||
}
|
||||
for (const filePath of allPaths) {
|
||||
const stat = await fs_1.promises.lstat(filePath);
|
||||
if (stat.isDirectory()) {
|
||||
continue;
|
||||
}
|
||||
const passThroughOptionsCopy = extend(true, {}, options.passthroughOptions);
|
||||
passThroughOptionsCopy.destination = filePath;
|
||||
if (options.prefix) {
|
||||
passThroughOptionsCopy.destination = path.join(options.prefix, passThroughOptionsCopy.destination);
|
||||
}
|
||||
promises.push(limit(() => this.bucket.upload(filePath, passThroughOptionsCopy)));
|
||||
}
|
||||
return Promise.all(promises);
|
||||
}
|
||||
/**
|
||||
* @typedef {object} DownloadManyFilesOptions
|
||||
* @property {number} [concurrencyLimit] The number of concurrently executing promises
|
||||
* to use when downloading the files.
|
||||
* @property {string} [prefix] A prefix to append to all of the downloaded files.
|
||||
* @property {string} [stripPrefix] A prefix to remove from all of the downloaded files.
|
||||
* @property {object} [passthroughOptions] {@link DownloadOptions} Options to be passed through
|
||||
* to each individual download operation.
|
||||
* @experimental
|
||||
*/
|
||||
/**
|
||||
* Download multiple files in parallel to the local filesystem. This is a convenience method
|
||||
* that utilizes {@link File#download} to perform the download.
|
||||
*
|
||||
* @param {array | string} [filesOrFolder] An array of file name strings or file objects to be downloaded. If
|
||||
* a string is provided this will be treated as a GCS prefix and all files with that prefix will be downloaded.
|
||||
* @param {DownloadManyFilesOptions} [options] Configuration options.
|
||||
* @returns {Promise<DownloadResponse[]>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
* const transferManager = new TransferManager(bucket);
|
||||
*
|
||||
* //-
|
||||
* // Download multiple files in parallel.
|
||||
* //-
|
||||
* const response = await transferManager.downloadManyFiles(['file1.txt', 'file2.txt']);
|
||||
* // The following files have been downloaded:
|
||||
* // - "file1.txt" (with the contents from my-bucket.file1.txt)
|
||||
* // - "file2.txt" (with the contents from my-bucket.file2.txt)
|
||||
* const response = await transferManager.downloadManyFiles([bucket.File('file1.txt'), bucket.File('file2.txt')]);
|
||||
* // The following files have been downloaded:
|
||||
* // - "file1.txt" (with the contents from my-bucket.file1.txt)
|
||||
* // - "file2.txt" (with the contents from my-bucket.file2.txt)
|
||||
* const response = await transferManager.downloadManyFiles('test-folder');
|
||||
* // All files with GCS prefix of 'test-folder' have been downloaded.
|
||||
* ```
|
||||
* @experimental
|
||||
*/
|
||||
async downloadManyFiles(filesOrFolder, options = {}) {
|
||||
const limit = pLimit(options.concurrencyLimit || DEFAULT_PARALLEL_DOWNLOAD_LIMIT);
|
||||
const promises = [];
|
||||
let files = [];
|
||||
if (!Array.isArray(filesOrFolder)) {
|
||||
const directoryFiles = await this.bucket.getFiles({
|
||||
prefix: filesOrFolder,
|
||||
});
|
||||
files = directoryFiles[0];
|
||||
}
|
||||
else {
|
||||
files = filesOrFolder.map(curFile => {
|
||||
if (typeof curFile === 'string') {
|
||||
return this.bucket.file(curFile);
|
||||
}
|
||||
return curFile;
|
||||
});
|
||||
}
|
||||
const stripRegexString = options.stripPrefix
|
||||
? `^${options.stripPrefix}`
|
||||
: EMPTY_REGEX;
|
||||
const regex = new RegExp(stripRegexString, 'g');
|
||||
for (const file of files) {
|
||||
const passThroughOptionsCopy = extend(true, {}, options.passthroughOptions);
|
||||
if (options.prefix) {
|
||||
passThroughOptionsCopy.destination = path.join(options.prefix || '', passThroughOptionsCopy.destination || '', file.name);
|
||||
}
|
||||
if (options.stripPrefix) {
|
||||
passThroughOptionsCopy.destination = file.name.replace(regex, '');
|
||||
}
|
||||
promises.push(limit(() => file.download(passThroughOptionsCopy)));
|
||||
}
|
||||
return Promise.all(promises);
|
||||
}
|
||||
/**
|
||||
* @typedef {object} DownloadFileInChunksOptions
|
||||
* @property {number} [concurrencyLimit] The number of concurrently executing promises
|
||||
* to use when downloading the file.
|
||||
* @property {number} [chunkSizeBytes] The size in bytes of each chunk to be downloaded.
|
||||
* @property {string | boolean} [validation] Whether or not to perform a CRC32C validation check when download is complete.
|
||||
* @experimental
|
||||
*/
|
||||
/**
|
||||
* Download a large file in chunks utilizing parallel download operations. This is a convenience method
|
||||
* that utilizes {@link File#download} to perform the download.
|
||||
*
|
||||
* @param {object} [file | string] {@link File} to download.
|
||||
* @param {DownloadFileInChunksOptions} [options] Configuration options.
|
||||
* @returns {Promise<DownloadResponse>}
|
||||
*
|
||||
* @example
|
||||
* ```
|
||||
* const {Storage} = require('@google-cloud/storage');
|
||||
* const storage = new Storage();
|
||||
* const bucket = storage.bucket('my-bucket');
|
||||
* const transferManager = new TransferManager(bucket);
|
||||
*
|
||||
* //-
|
||||
* // Download a large file in chunks utilizing parallel operations.
|
||||
* //-
|
||||
* const response = await transferManager.downloadLargeFile(bucket.file('large-file.txt');
|
||||
* // Your local directory now contains:
|
||||
* // - "large-file.txt" (with the contents from my-bucket.large-file.txt)
|
||||
* ```
|
||||
* @experimental
|
||||
*/
|
||||
async downloadFileInChunks(fileOrName, options = {}) {
|
||||
let chunkSize = options.chunkSizeBytes || DOWNLOAD_IN_CHUNKS_DEFAULT_CHUNK_SIZE;
|
||||
let limit = pLimit(options.concurrencyLimit || DEFAULT_PARALLEL_CHUNKED_DOWNLOAD_LIMIT);
|
||||
const promises = [];
|
||||
const file = typeof fileOrName === 'string'
|
||||
? this.bucket.file(fileOrName)
|
||||
: fileOrName;
|
||||
const fileInfo = await file.get();
|
||||
const size = parseInt(fileInfo[0].metadata.size);
|
||||
// If the file size does not meet the threshold download it as a single chunk.
|
||||
if (size < DOWNLOAD_IN_CHUNKS_FILE_SIZE_THRESHOLD) {
|
||||
limit = pLimit(1);
|
||||
chunkSize = size;
|
||||
}
|
||||
let start = 0;
|
||||
const filePath = options.destination || path.basename(file.name);
|
||||
const fileToWrite = await fs_1.promises.open(filePath, 'w+');
|
||||
while (start < size) {
|
||||
const chunkStart = start;
|
||||
let chunkEnd = start + chunkSize - 1;
|
||||
chunkEnd = chunkEnd > size ? size : chunkEnd;
|
||||
promises.push(limit(() => file.download({ start: chunkStart, end: chunkEnd }).then(resp => {
|
||||
return fileToWrite.write(resp[0], 0, resp[0].length, chunkStart);
|
||||
})));
|
||||
start += chunkSize;
|
||||
}
|
||||
return new Promise((resolve, reject) => {
|
||||
let results;
|
||||
Promise.all(promises)
|
||||
.then(data => {
|
||||
results = data.map(result => result.buffer);
|
||||
if (options.validation === 'crc32c') {
|
||||
return crc32c_1.CRC32C.fromFile(filePath);
|
||||
}
|
||||
return;
|
||||
})
|
||||
.then(() => {
|
||||
resolve(results);
|
||||
})
|
||||
.catch(e => {
|
||||
reject(e);
|
||||
})
|
||||
.finally(() => {
|
||||
fileToWrite.close();
|
||||
});
|
||||
});
|
||||
}
|
||||
async *getPathsFromDirectory(directory) {
|
||||
const filesAndSubdirectories = await fs_1.promises.readdir(directory, {
|
||||
withFileTypes: true,
|
||||
});
|
||||
for (const curFileOrDirectory of filesAndSubdirectories) {
|
||||
const fullPath = path.join(directory, curFileOrDirectory.name);
|
||||
curFileOrDirectory.isDirectory()
|
||||
? yield* this.getPathsFromDirectory(fullPath)
|
||||
: yield fullPath;
|
||||
}
|
||||
}
|
||||
}
|
||||
exports.TransferManager = TransferManager;
|
||||
//# sourceMappingURL=transfer-manager.js.map
|
||||
@ -0,0 +1,76 @@
|
||||
/// <reference types="node" />
|
||||
/// <reference types="node" />
|
||||
/// <reference types="node" />
|
||||
import * as querystring from 'querystring';
|
||||
import { PassThrough } from 'stream';
|
||||
export declare function normalize<T = {}, U = Function>(optionsOrCallback?: T | U, cb?: U): {
|
||||
options: T;
|
||||
callback: U;
|
||||
};
|
||||
/**
|
||||
* Flatten an object into an Array of arrays, [[key, value], ..].
|
||||
* Implements Object.entries() for Node.js <8
|
||||
* @internal
|
||||
*/
|
||||
export declare function objectEntries<T>(obj: {
|
||||
[key: string]: T;
|
||||
}): Array<[string, T]>;
|
||||
/**
|
||||
* Encode `str` with encodeURIComponent, plus these
|
||||
* reserved characters: `! * ' ( )`.
|
||||
*
|
||||
* See {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/encodeURIComponent| MDN: fixedEncodeURIComponent}
|
||||
*
|
||||
* @param {string} str The URI component to encode.
|
||||
* @return {string} The encoded string.
|
||||
*/
|
||||
export declare function fixedEncodeURIComponent(str: string): string;
|
||||
/**
|
||||
* URI encode `uri` for generating signed URLs, using fixedEncodeURIComponent.
|
||||
*
|
||||
* Encode every byte except `A-Z a-Z 0-9 ~ - . _`.
|
||||
*
|
||||
* @param {string} uri The URI to encode.
|
||||
* @param [boolean=false] encodeSlash If `true`, the "/" character is not encoded.
|
||||
* @return {string} The encoded string.
|
||||
*/
|
||||
export declare function encodeURI(uri: string, encodeSlash: boolean): string;
|
||||
/**
|
||||
* Serialize an object to a URL query string using util.encodeURI(uri, true).
|
||||
* @param {string} url The object to serialize.
|
||||
* @return {string} Serialized string.
|
||||
*/
|
||||
export declare function qsStringify(qs: querystring.ParsedUrlQueryInput): string;
|
||||
export declare function objectKeyToLowercase<T>(object: {
|
||||
[key: string]: T;
|
||||
}): {
|
||||
[key: string]: T;
|
||||
};
|
||||
/**
|
||||
* JSON encode str, with unicode \u+ representation.
|
||||
* @param {object} obj The object to encode.
|
||||
* @return {string} Serialized string.
|
||||
*/
|
||||
export declare function unicodeJSONStringify(obj: object): string;
|
||||
/**
|
||||
* Converts the given objects keys to snake_case
|
||||
* @param {object} obj object to convert keys to snake case.
|
||||
* @returns {object} object with keys converted to snake case.
|
||||
*/
|
||||
export declare function convertObjKeysToSnakeCase(obj: object): object;
|
||||
/**
|
||||
* Formats the provided date object as a UTC ISO string.
|
||||
* @param {Date} dateTimeToFormat date object to be formatted.
|
||||
* @param {boolean} includeTime flag to include hours, minutes, seconds in output.
|
||||
* @param {string} dateDelimiter delimiter between date components.
|
||||
* @param {string} timeDelimiter delimiter between time components.
|
||||
* @returns {string} UTC ISO format of provided date obect.
|
||||
*/
|
||||
export declare function formatAsUTCISO(dateTimeToFormat: Date, includeTime?: boolean, dateDelimiter?: string, timeDelimiter?: string): string;
|
||||
export declare class PassThroughShim extends PassThrough {
|
||||
private shouldEmitReading;
|
||||
private shouldEmitWriting;
|
||||
_read(size: number): void;
|
||||
_write(chunk: never, encoding: BufferEncoding, callback: (error?: Error | null | undefined) => void): void;
|
||||
_final(callback: (error?: Error | null | undefined) => void): void;
|
||||
}
|
||||
@ -0,0 +1,186 @@
|
||||
"use strict";
|
||||
// Copyright 2019 Google LLC
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.PassThroughShim = exports.formatAsUTCISO = exports.convertObjKeysToSnakeCase = exports.unicodeJSONStringify = exports.objectKeyToLowercase = exports.qsStringify = exports.encodeURI = exports.fixedEncodeURIComponent = exports.objectEntries = exports.normalize = void 0;
|
||||
const querystring = require("querystring");
|
||||
const stream_1 = require("stream");
|
||||
function normalize(optionsOrCallback, cb) {
|
||||
const options = (typeof optionsOrCallback === 'object' ? optionsOrCallback : {});
|
||||
const callback = (typeof optionsOrCallback === 'function' ? optionsOrCallback : cb);
|
||||
return { options, callback };
|
||||
}
|
||||
exports.normalize = normalize;
|
||||
/**
|
||||
* Flatten an object into an Array of arrays, [[key, value], ..].
|
||||
* Implements Object.entries() for Node.js <8
|
||||
* @internal
|
||||
*/
|
||||
function objectEntries(obj) {
|
||||
return Object.keys(obj).map(key => [key, obj[key]]);
|
||||
}
|
||||
exports.objectEntries = objectEntries;
|
||||
/**
|
||||
* Encode `str` with encodeURIComponent, plus these
|
||||
* reserved characters: `! * ' ( )`.
|
||||
*
|
||||
* See {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/encodeURIComponent| MDN: fixedEncodeURIComponent}
|
||||
*
|
||||
* @param {string} str The URI component to encode.
|
||||
* @return {string} The encoded string.
|
||||
*/
|
||||
function fixedEncodeURIComponent(str) {
|
||||
return encodeURIComponent(str).replace(/[!'()*]/g, c => '%' + c.charCodeAt(0).toString(16).toUpperCase());
|
||||
}
|
||||
exports.fixedEncodeURIComponent = fixedEncodeURIComponent;
|
||||
/**
|
||||
* URI encode `uri` for generating signed URLs, using fixedEncodeURIComponent.
|
||||
*
|
||||
* Encode every byte except `A-Z a-Z 0-9 ~ - . _`.
|
||||
*
|
||||
* @param {string} uri The URI to encode.
|
||||
* @param [boolean=false] encodeSlash If `true`, the "/" character is not encoded.
|
||||
* @return {string} The encoded string.
|
||||
*/
|
||||
function encodeURI(uri, encodeSlash) {
|
||||
// Split the string by `/`, and conditionally rejoin them with either
|
||||
// %2F if encodeSlash is `true`, or '/' if `false`.
|
||||
return uri
|
||||
.split('/')
|
||||
.map(fixedEncodeURIComponent)
|
||||
.join(encodeSlash ? '%2F' : '/');
|
||||
}
|
||||
exports.encodeURI = encodeURI;
|
||||
/**
|
||||
* Serialize an object to a URL query string using util.encodeURI(uri, true).
|
||||
* @param {string} url The object to serialize.
|
||||
* @return {string} Serialized string.
|
||||
*/
|
||||
function qsStringify(qs) {
|
||||
return querystring.stringify(qs, '&', '=', {
|
||||
encodeURIComponent: (component) => encodeURI(component, true),
|
||||
});
|
||||
}
|
||||
exports.qsStringify = qsStringify;
|
||||
function objectKeyToLowercase(object) {
|
||||
const newObj = {};
|
||||
for (let key of Object.keys(object)) {
|
||||
const value = object[key];
|
||||
key = key.toLowerCase();
|
||||
newObj[key] = value;
|
||||
}
|
||||
return newObj;
|
||||
}
|
||||
exports.objectKeyToLowercase = objectKeyToLowercase;
|
||||
/**
|
||||
* JSON encode str, with unicode \u+ representation.
|
||||
* @param {object} obj The object to encode.
|
||||
* @return {string} Serialized string.
|
||||
*/
|
||||
function unicodeJSONStringify(obj) {
|
||||
return JSON.stringify(obj).replace(/[\u0080-\uFFFF]/g, (char) => '\\u' + ('0000' + char.charCodeAt(0).toString(16)).slice(-4));
|
||||
}
|
||||
exports.unicodeJSONStringify = unicodeJSONStringify;
|
||||
/**
|
||||
* Converts the given objects keys to snake_case
|
||||
* @param {object} obj object to convert keys to snake case.
|
||||
* @returns {object} object with keys converted to snake case.
|
||||
*/
|
||||
function convertObjKeysToSnakeCase(obj) {
|
||||
if (obj instanceof Date || obj instanceof RegExp) {
|
||||
return obj;
|
||||
}
|
||||
if (Array.isArray(obj)) {
|
||||
return obj.map(convertObjKeysToSnakeCase);
|
||||
}
|
||||
if (obj instanceof Object) {
|
||||
return Object.keys(obj).reduce((acc, cur) => {
|
||||
const s = cur[0].toLocaleLowerCase() +
|
||||
cur.slice(1).replace(/([A-Z]+)/g, (match, p1) => {
|
||||
return `_${p1.toLowerCase()}`;
|
||||
});
|
||||
acc[s] = convertObjKeysToSnakeCase(obj[cur]);
|
||||
return acc;
|
||||
}, Object());
|
||||
}
|
||||
return obj;
|
||||
}
|
||||
exports.convertObjKeysToSnakeCase = convertObjKeysToSnakeCase;
|
||||
/**
|
||||
* Formats the provided date object as a UTC ISO string.
|
||||
* @param {Date} dateTimeToFormat date object to be formatted.
|
||||
* @param {boolean} includeTime flag to include hours, minutes, seconds in output.
|
||||
* @param {string} dateDelimiter delimiter between date components.
|
||||
* @param {string} timeDelimiter delimiter between time components.
|
||||
* @returns {string} UTC ISO format of provided date obect.
|
||||
*/
|
||||
function formatAsUTCISO(dateTimeToFormat, includeTime = false, dateDelimiter = '', timeDelimiter = '') {
|
||||
const year = dateTimeToFormat.getUTCFullYear();
|
||||
const month = dateTimeToFormat.getUTCMonth() + 1;
|
||||
const day = dateTimeToFormat.getUTCDate();
|
||||
const hour = dateTimeToFormat.getUTCHours();
|
||||
const minute = dateTimeToFormat.getUTCMinutes();
|
||||
const second = dateTimeToFormat.getUTCSeconds();
|
||||
let resultString = `${year.toString().padStart(4, '0')}${dateDelimiter}${month
|
||||
.toString()
|
||||
.padStart(2, '0')}${dateDelimiter}${day.toString().padStart(2, '0')}`;
|
||||
if (includeTime) {
|
||||
resultString = `${resultString}T${hour
|
||||
.toString()
|
||||
.padStart(2, '0')}${timeDelimiter}${minute
|
||||
.toString()
|
||||
.padStart(2, '0')}${timeDelimiter}${second.toString().padStart(2, '0')}Z`;
|
||||
}
|
||||
return resultString;
|
||||
}
|
||||
exports.formatAsUTCISO = formatAsUTCISO;
|
||||
class PassThroughShim extends stream_1.PassThrough {
|
||||
constructor() {
|
||||
super(...arguments);
|
||||
this.shouldEmitReading = true;
|
||||
this.shouldEmitWriting = true;
|
||||
}
|
||||
_read(size) {
|
||||
if (this.shouldEmitReading) {
|
||||
this.emit('reading');
|
||||
this.shouldEmitReading = false;
|
||||
}
|
||||
super._read(size);
|
||||
}
|
||||
_write(chunk, encoding, callback) {
|
||||
if (this.shouldEmitWriting) {
|
||||
this.emit('writing');
|
||||
this.shouldEmitWriting = false;
|
||||
}
|
||||
// Per the nodejs documention, callback must be invoked on the next tick
|
||||
process.nextTick(() => {
|
||||
super._write(chunk, encoding, callback);
|
||||
});
|
||||
}
|
||||
_final(callback) {
|
||||
// If the stream is empty (i.e. empty file) final will be invoked before _read / _write
|
||||
// and we should still emit the proper events.
|
||||
if (this.shouldEmitReading) {
|
||||
this.emit('reading');
|
||||
this.shouldEmitReading = false;
|
||||
}
|
||||
if (this.shouldEmitWriting) {
|
||||
this.emit('writing');
|
||||
this.shouldEmitWriting = false;
|
||||
}
|
||||
callback(null);
|
||||
}
|
||||
}
|
||||
exports.PassThroughShim = PassThroughShim;
|
||||
//# sourceMappingURL=util.js.map
|
||||
@ -0,0 +1 @@
|
||||
../mime/cli.js
|
||||
@ -0,0 +1,21 @@
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2010 Benjamin Thomas, Robert Kieffer
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
@ -0,0 +1,97 @@
|
||||
'use strict';
|
||||
|
||||
/**
|
||||
* @param typeMap [Object] Map of MIME type -> Array[extensions]
|
||||
* @param ...
|
||||
*/
|
||||
function Mime() {
|
||||
this._types = Object.create(null);
|
||||
this._extensions = Object.create(null);
|
||||
|
||||
for (let i = 0; i < arguments.length; i++) {
|
||||
this.define(arguments[i]);
|
||||
}
|
||||
|
||||
this.define = this.define.bind(this);
|
||||
this.getType = this.getType.bind(this);
|
||||
this.getExtension = this.getExtension.bind(this);
|
||||
}
|
||||
|
||||
/**
|
||||
* Define mimetype -> extension mappings. Each key is a mime-type that maps
|
||||
* to an array of extensions associated with the type. The first extension is
|
||||
* used as the default extension for the type.
|
||||
*
|
||||
* e.g. mime.define({'audio/ogg', ['oga', 'ogg', 'spx']});
|
||||
*
|
||||
* If a type declares an extension that has already been defined, an error will
|
||||
* be thrown. To suppress this error and force the extension to be associated
|
||||
* with the new type, pass `force`=true. Alternatively, you may prefix the
|
||||
* extension with "*" to map the type to extension, without mapping the
|
||||
* extension to the type.
|
||||
*
|
||||
* e.g. mime.define({'audio/wav', ['wav']}, {'audio/x-wav', ['*wav']});
|
||||
*
|
||||
*
|
||||
* @param map (Object) type definitions
|
||||
* @param force (Boolean) if true, force overriding of existing definitions
|
||||
*/
|
||||
Mime.prototype.define = function(typeMap, force) {
|
||||
for (let type in typeMap) {
|
||||
let extensions = typeMap[type].map(function(t) {
|
||||
return t.toLowerCase();
|
||||
});
|
||||
type = type.toLowerCase();
|
||||
|
||||
for (let i = 0; i < extensions.length; i++) {
|
||||
const ext = extensions[i];
|
||||
|
||||
// '*' prefix = not the preferred type for this extension. So fixup the
|
||||
// extension, and skip it.
|
||||
if (ext[0] === '*') {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!force && (ext in this._types)) {
|
||||
throw new Error(
|
||||
'Attempt to change mapping for "' + ext +
|
||||
'" extension from "' + this._types[ext] + '" to "' + type +
|
||||
'". Pass `force=true` to allow this, otherwise remove "' + ext +
|
||||
'" from the list of extensions for "' + type + '".'
|
||||
);
|
||||
}
|
||||
|
||||
this._types[ext] = type;
|
||||
}
|
||||
|
||||
// Use first extension as default
|
||||
if (force || !this._extensions[type]) {
|
||||
const ext = extensions[0];
|
||||
this._extensions[type] = (ext[0] !== '*') ? ext : ext.substr(1);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Lookup a mime type based on extension
|
||||
*/
|
||||
Mime.prototype.getType = function(path) {
|
||||
path = String(path);
|
||||
let last = path.replace(/^.*[/\\]/, '').toLowerCase();
|
||||
let ext = last.replace(/^.*\./, '').toLowerCase();
|
||||
|
||||
let hasPath = last.length < path.length;
|
||||
let hasDot = ext.length < last.length - 1;
|
||||
|
||||
return (hasDot || !hasPath) && this._types[ext] || null;
|
||||
};
|
||||
|
||||
/**
|
||||
* Return file extension associated with a mime type
|
||||
*/
|
||||
Mime.prototype.getExtension = function(type) {
|
||||
type = /^\s*([^;\s]*)/.test(type) && RegExp.$1;
|
||||
return type && this._extensions[type.toLowerCase()] || null;
|
||||
};
|
||||
|
||||
module.exports = Mime;
|
||||
@ -0,0 +1,178 @@
|
||||
<!--
|
||||
-- This file is auto-generated from src/README_js.md. Changes should be made there.
|
||||
-->
|
||||
# Mime
|
||||
|
||||
A comprehensive, compact MIME type module.
|
||||
|
||||
[](https://travis-ci.org/broofa/mime)
|
||||
|
||||
## Install
|
||||
|
||||
### NPM
|
||||
```
|
||||
npm install mime
|
||||
```
|
||||
|
||||
### Browser
|
||||
|
||||
It is recommended that you use a bundler such as
|
||||
[webpack](https://webpack.github.io/) or [browserify](http://browserify.org/) to
|
||||
package your code. However, browser-ready versions are available via
|
||||
skypack.dev as follows:
|
||||
```
|
||||
// Full version
|
||||
<script type="module">
|
||||
import mime from "https://cdn.skypack.dev/mime";
|
||||
</script>
|
||||
```
|
||||
|
||||
```
|
||||
// "lite" version
|
||||
<script type="module">
|
||||
import mime from "https://cdn.skypack.dev/mime/lite";
|
||||
</script>
|
||||
```
|
||||
|
||||
## Quick Start
|
||||
|
||||
For the full version (800+ MIME types, 1,000+ extensions):
|
||||
|
||||
```javascript
|
||||
const mime = require('mime');
|
||||
|
||||
mime.getType('txt'); // ⇨ 'text/plain'
|
||||
mime.getExtension('text/plain'); // ⇨ 'txt'
|
||||
```
|
||||
|
||||
See [Mime API](#mime-api) below for API details.
|
||||
|
||||
## Lite Version
|
||||
|
||||
The "lite" version of this module omits vendor-specific (`*/vnd.*`) and
|
||||
experimental (`*/x-*`) types. It weighs in at ~2.5KB, compared to 8KB for the
|
||||
full version. To load the lite version:
|
||||
|
||||
```javascript
|
||||
const mime = require('mime/lite');
|
||||
```
|
||||
|
||||
## Mime .vs. mime-types .vs. mime-db modules
|
||||
|
||||
For those of you wondering about the difference between these [popular] NPM modules,
|
||||
here's a brief rundown ...
|
||||
|
||||
[`mime-db`](https://github.com/jshttp/mime-db) is "the source of
|
||||
truth" for MIME type information. It is not an API. Rather, it is a canonical
|
||||
dataset of mime type definitions pulled from IANA, Apache, NGINX, and custom mappings
|
||||
submitted by the Node.js community.
|
||||
|
||||
[`mime-types`](https://github.com/jshttp/mime-types) is a thin
|
||||
wrapper around mime-db that provides an API drop-in compatible(ish) with `mime @ < v1.3.6` API.
|
||||
|
||||
`mime` is, as of v2, a self-contained module bundled with a pre-optimized version
|
||||
of the `mime-db` dataset. It provides a simplified API with the following characteristics:
|
||||
|
||||
* Intelligently resolved type conflicts (See [mime-score](https://github.com/broofa/mime-score) for details)
|
||||
* Method naming consistent with industry best-practices
|
||||
* Compact footprint. E.g. The minified+compressed sizes of the various modules:
|
||||
|
||||
Module | Size
|
||||
--- | ---
|
||||
`mime-db` | 18 KB
|
||||
`mime-types` | same as mime-db
|
||||
`mime` | 8 KB
|
||||
`mime/lite` | 2 KB
|
||||
|
||||
## Mime API
|
||||
|
||||
Both `require('mime')` and `require('mime/lite')` return instances of the MIME
|
||||
class, documented below.
|
||||
|
||||
Note: Inputs to this API are case-insensitive. Outputs (returned values) will
|
||||
be lowercase.
|
||||
|
||||
### new Mime(typeMap, ... more maps)
|
||||
|
||||
Most users of this module will not need to create Mime instances directly.
|
||||
However if you would like to create custom mappings, you may do so as follows
|
||||
...
|
||||
|
||||
```javascript
|
||||
// Require Mime class
|
||||
const Mime = require('mime/Mime');
|
||||
|
||||
// Define mime type -> extensions map
|
||||
const typeMap = {
|
||||
'text/abc': ['abc', 'alpha', 'bet'],
|
||||
'text/def': ['leppard']
|
||||
};
|
||||
|
||||
// Create and use Mime instance
|
||||
const myMime = new Mime(typeMap);
|
||||
myMime.getType('abc'); // ⇨ 'text/abc'
|
||||
myMime.getExtension('text/def'); // ⇨ 'leppard'
|
||||
```
|
||||
|
||||
If more than one map argument is provided, each map is `define()`ed (see below), in order.
|
||||
|
||||
### mime.getType(pathOrExtension)
|
||||
|
||||
Get mime type for the given path or extension. E.g.
|
||||
|
||||
```javascript
|
||||
mime.getType('js'); // ⇨ 'application/javascript'
|
||||
mime.getType('json'); // ⇨ 'application/json'
|
||||
|
||||
mime.getType('txt'); // ⇨ 'text/plain'
|
||||
mime.getType('dir/text.txt'); // ⇨ 'text/plain'
|
||||
mime.getType('dir\\text.txt'); // ⇨ 'text/plain'
|
||||
mime.getType('.text.txt'); // ⇨ 'text/plain'
|
||||
mime.getType('.txt'); // ⇨ 'text/plain'
|
||||
```
|
||||
|
||||
`null` is returned in cases where an extension is not detected or recognized
|
||||
|
||||
```javascript
|
||||
mime.getType('foo/txt'); // ⇨ null
|
||||
mime.getType('bogus_type'); // ⇨ null
|
||||
```
|
||||
|
||||
### mime.getExtension(type)
|
||||
Get extension for the given mime type. Charset options (often included in
|
||||
Content-Type headers) are ignored.
|
||||
|
||||
```javascript
|
||||
mime.getExtension('text/plain'); // ⇨ 'txt'
|
||||
mime.getExtension('application/json'); // ⇨ 'json'
|
||||
mime.getExtension('text/html; charset=utf8'); // ⇨ 'html'
|
||||
```
|
||||
|
||||
### mime.define(typeMap[, force = false])
|
||||
|
||||
Define [more] type mappings.
|
||||
|
||||
`typeMap` is a map of type -> extensions, as documented in `new Mime`, above.
|
||||
|
||||
By default this method will throw an error if you try to map a type to an
|
||||
extension that is already assigned to another type. Passing `true` for the
|
||||
`force` argument will suppress this behavior (overriding any previous mapping).
|
||||
|
||||
```javascript
|
||||
mime.define({'text/x-abc': ['abc', 'abcd']});
|
||||
|
||||
mime.getType('abcd'); // ⇨ 'text/x-abc'
|
||||
mime.getExtension('text/x-abc') // ⇨ 'abc'
|
||||
```
|
||||
|
||||
## Command Line
|
||||
|
||||
mime [path_or_extension]
|
||||
|
||||
E.g.
|
||||
|
||||
> mime scripts/jquery.js
|
||||
application/javascript
|
||||
|
||||
----
|
||||
Markdown generated from [src/README_js.md](src/README_js.md) by [](https://github.com/broofa/runmd)
|
||||
@ -0,0 +1,46 @@
|
||||
#!/usr/bin/env node
|
||||
|
||||
'use strict';
|
||||
|
||||
process.title = 'mime';
|
||||
let mime = require('.');
|
||||
let pkg = require('./package.json');
|
||||
let args = process.argv.splice(2);
|
||||
|
||||
if (args.includes('--version') || args.includes('-v') || args.includes('--v')) {
|
||||
console.log(pkg.version);
|
||||
process.exit(0);
|
||||
} else if (args.includes('--name') || args.includes('-n') || args.includes('--n')) {
|
||||
console.log(pkg.name);
|
||||
process.exit(0);
|
||||
} else if (args.includes('--help') || args.includes('-h') || args.includes('--h')) {
|
||||
console.log(pkg.name + ' - ' + pkg.description + '\n');
|
||||
console.log(`Usage:
|
||||
|
||||
mime [flags] [path_or_extension]
|
||||
|
||||
Flags:
|
||||
--help, -h Show this message
|
||||
--version, -v Display the version
|
||||
--name, -n Print the name of the program
|
||||
|
||||
Note: the command will exit after it executes if a command is specified
|
||||
The path_or_extension is the path to the file or the extension of the file.
|
||||
|
||||
Examples:
|
||||
mime --help
|
||||
mime --version
|
||||
mime --name
|
||||
mime -v
|
||||
mime src/log.js
|
||||
mime new.py
|
||||
mime foo.sh
|
||||
`);
|
||||
process.exit(0);
|
||||
}
|
||||
|
||||
let file = args[0];
|
||||
let type = mime.getType(file);
|
||||
|
||||
process.stdout.write(type + '\n');
|
||||
|
||||
@ -0,0 +1,4 @@
|
||||
'use strict';
|
||||
|
||||
let Mime = require('./Mime');
|
||||
module.exports = new Mime(require('./types/standard'), require('./types/other'));
|
||||
@ -0,0 +1,4 @@
|
||||
'use strict';
|
||||
|
||||
let Mime = require('./Mime');
|
||||
module.exports = new Mime(require('./types/standard'));
|
||||
@ -0,0 +1,52 @@
|
||||
{
|
||||
"author": {
|
||||
"name": "Robert Kieffer",
|
||||
"url": "http://github.com/broofa",
|
||||
"email": "robert@broofa.com"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=10.0.0"
|
||||
},
|
||||
"bin": {
|
||||
"mime": "cli.js"
|
||||
},
|
||||
"contributors": [],
|
||||
"description": "A comprehensive library for mime-type mapping",
|
||||
"license": "MIT",
|
||||
"dependencies": {},
|
||||
"devDependencies": {
|
||||
"benchmark": "*",
|
||||
"chalk": "4.1.2",
|
||||
"eslint": "8.1.0",
|
||||
"mime-db": "1.50.0",
|
||||
"mime-score": "1.2.0",
|
||||
"mime-types": "2.1.33",
|
||||
"mocha": "9.1.3",
|
||||
"runmd": "*",
|
||||
"standard-version": "9.3.2"
|
||||
},
|
||||
"files": [
|
||||
"index.js",
|
||||
"lite.js",
|
||||
"Mime.js",
|
||||
"cli.js",
|
||||
"/types"
|
||||
],
|
||||
"scripts": {
|
||||
"prepare": "node src/build.js && runmd --output README.md src/README_js.md",
|
||||
"release": "standard-version",
|
||||
"benchmark": "node src/benchmark.js",
|
||||
"md": "runmd --watch --output README.md src/README_js.md",
|
||||
"test": "mocha src/test.js"
|
||||
},
|
||||
"keywords": [
|
||||
"util",
|
||||
"mime"
|
||||
],
|
||||
"name": "mime",
|
||||
"repository": {
|
||||
"url": "https://github.com/broofa/mime",
|
||||
"type": "git"
|
||||
},
|
||||
"version": "3.0.0"
|
||||
}
|
||||
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@ -0,0 +1,108 @@
|
||||
{
|
||||
"name": "@google-cloud/storage",
|
||||
"description": "Cloud Storage Client Library for Node.js",
|
||||
"version": "6.10.1",
|
||||
"license": "Apache-2.0",
|
||||
"author": "Google Inc.",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
},
|
||||
"repository": "googleapis/nodejs-storage",
|
||||
"main": "./build/src/index.js",
|
||||
"types": "./build/src/index.d.ts",
|
||||
"files": [
|
||||
"build/src",
|
||||
"!build/src/**/*.map"
|
||||
],
|
||||
"keywords": [
|
||||
"google apis client",
|
||||
"google api client",
|
||||
"google apis",
|
||||
"google api",
|
||||
"google",
|
||||
"google cloud platform",
|
||||
"google cloud",
|
||||
"cloud",
|
||||
"google storage",
|
||||
"storage"
|
||||
],
|
||||
"scripts": {
|
||||
"predocs": "npm run compile",
|
||||
"docs": "jsdoc -c .jsdoc.js",
|
||||
"system-test": "mocha build/system-test --timeout 600000 --exit",
|
||||
"conformance-test": "mocha --parallel build/conformance-test/ --require build/conformance-test/globalHooks.js",
|
||||
"preconformance-test": "npm run compile",
|
||||
"presystem-test": "npm run compile",
|
||||
"test": "c8 mocha build/test",
|
||||
"pretest": "npm run compile",
|
||||
"lint": "gts check",
|
||||
"samples-test": "npm link && cd samples/ && npm link ../ && npm test && cd ../",
|
||||
"all-test": "npm test && npm run system-test && npm run samples-test",
|
||||
"check": "gts check",
|
||||
"clean": "gts clean",
|
||||
"compile": "tsc -p .",
|
||||
"fix": "gts fix",
|
||||
"prepare": "npm run compile",
|
||||
"docs-test": "linkinator docs",
|
||||
"predocs-test": "npm run docs",
|
||||
"benchwrapper": "node bin/benchwrapper.js",
|
||||
"prelint": "cd samples; npm link ../; npm install",
|
||||
"precompile": "gts clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@google-cloud/paginator": "^3.0.7",
|
||||
"@google-cloud/projectify": "^3.0.0",
|
||||
"@google-cloud/promisify": "^3.0.0",
|
||||
"abort-controller": "^3.0.0",
|
||||
"async-retry": "^1.3.3",
|
||||
"compressible": "^2.0.12",
|
||||
"duplexify": "^4.0.0",
|
||||
"ent": "^2.2.0",
|
||||
"extend": "^3.0.2",
|
||||
"gaxios": "^5.0.0",
|
||||
"google-auth-library": "^8.0.1",
|
||||
"mime": "^3.0.0",
|
||||
"mime-types": "^2.0.8",
|
||||
"p-limit": "^3.0.1",
|
||||
"retry-request": "^5.0.0",
|
||||
"teeny-request": "^8.0.0",
|
||||
"uuid": "^8.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@google-cloud/pubsub": "^3.0.0",
|
||||
"@grpc/grpc-js": "^1.0.3",
|
||||
"@grpc/proto-loader": "^0.7.0",
|
||||
"@types/async-retry": "^1.4.3",
|
||||
"@types/compressible": "^2.0.0",
|
||||
"@types/ent": "^2.2.1",
|
||||
"@types/extend": "^3.0.0",
|
||||
"@types/mime": "^3.0.0",
|
||||
"@types/mime-types": "^2.1.0",
|
||||
"@types/mocha": "^9.1.1",
|
||||
"@types/mockery": "^1.4.29",
|
||||
"@types/node": "^18.0.0",
|
||||
"@types/node-fetch": "^2.1.3",
|
||||
"@types/proxyquire": "^1.3.28",
|
||||
"@types/request": "^2.48.4",
|
||||
"@types/sinon": "^10.0.0",
|
||||
"@types/tmp": "0.2.3",
|
||||
"@types/uuid": "^8.0.0",
|
||||
"@types/yargs": "^17.0.10",
|
||||
"c8": "^7.0.0",
|
||||
"form-data": "^4.0.0",
|
||||
"gts": "^3.1.0",
|
||||
"jsdoc": "^4.0.0",
|
||||
"jsdoc-fresh": "^2.0.0",
|
||||
"jsdoc-region-tag": "^2.0.0",
|
||||
"linkinator": "^4.0.0",
|
||||
"mocha": "^9.2.2",
|
||||
"mockery": "^2.1.0",
|
||||
"nock": "~13.3.0",
|
||||
"node-fetch": "^2.6.7",
|
||||
"proxyquire": "^2.1.3",
|
||||
"sinon": "^15.0.0",
|
||||
"tmp": "^0.2.0",
|
||||
"typescript": "^4.6.4",
|
||||
"yargs": "^17.3.1"
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,19 @@
|
||||
[](https://www.npmjs.com/package/@tokenizer/token)
|
||||
[](https://npmcharts.com/compare/@tokenizer/token?interval=30)
|
||||
|
||||
# @tokenizer/token
|
||||
|
||||
TypeScript definition of an [strtok3](https://github.com/Borewit/strtok3) token.
|
||||
|
||||
## Licence
|
||||
|
||||
(The MIT License)
|
||||
|
||||
Copyright (c) 2020 Borewit
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the 'Software'), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
|
||||
@ -0,0 +1,30 @@
|
||||
/**
|
||||
* Read-only token
|
||||
* See https://github.com/Borewit/strtok3 for more information
|
||||
*/
|
||||
export interface IGetToken<Value, Array extends Uint8Array = Uint8Array> {
|
||||
|
||||
/**
|
||||
* Length of encoded token in bytes
|
||||
*/
|
||||
len: number;
|
||||
|
||||
/**
|
||||
* Decode value from buffer at offset
|
||||
* @param array - Uint8Array to read the decoded value from
|
||||
* @param offset - Decode offset
|
||||
* @return decoded value
|
||||
*/
|
||||
get(array: Array, offset: number): Value;
|
||||
}
|
||||
|
||||
export interface IToken<Value, Array extends Uint8Array = Uint8Array> extends IGetToken<Value, Array> {
|
||||
/**
|
||||
* Encode value to buffer
|
||||
* @param array - Uint8Array to write the encoded value to
|
||||
* @param offset - Buffer write offset
|
||||
* @param value - Value to decode of type T
|
||||
* @return offset plus number of bytes written
|
||||
*/
|
||||
put(array: Array, offset: number, value: Value): number
|
||||
}
|
||||
@ -0,0 +1,33 @@
|
||||
{
|
||||
"name": "@tokenizer/token",
|
||||
"version": "0.3.0",
|
||||
"description": "TypeScript definition for strtok3 token",
|
||||
"main": "",
|
||||
"types": "index.d.ts",
|
||||
"files": [
|
||||
"index.d.ts"
|
||||
],
|
||||
"keywords": [
|
||||
"token",
|
||||
"interface",
|
||||
"tokenizer",
|
||||
"TypeScript"
|
||||
],
|
||||
"author": {
|
||||
"name": "Borewit",
|
||||
"url": "https://github.com/Borewit"
|
||||
},
|
||||
"license": "MIT",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/Borewit/tokenizer-token.git"
|
||||
},
|
||||
"bugs": {
|
||||
"url": "https://github.com/Borewit/tokenizer-token/issues"
|
||||
},
|
||||
"typeScriptVersion": "3.0",
|
||||
"dependencies": {},
|
||||
"devDependencies": {
|
||||
"@types/node": "^13.1.0"
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,38 @@
|
||||
/**
|
||||
Convert a value to an array.
|
||||
|
||||
_Supplying `null` or `undefined` results in an empty array._
|
||||
|
||||
@example
|
||||
```
|
||||
import arrify = require('arrify');
|
||||
|
||||
arrify('🦄');
|
||||
//=> ['🦄']
|
||||
|
||||
arrify(['🦄']);
|
||||
//=> ['🦄']
|
||||
|
||||
arrify(new Set(['🦄']));
|
||||
//=> ['🦄']
|
||||
|
||||
arrify(null);
|
||||
//=> []
|
||||
|
||||
arrify(undefined);
|
||||
//=> []
|
||||
```
|
||||
*/
|
||||
declare function arrify<ValueType>(
|
||||
value: ValueType
|
||||
): ValueType extends (null | undefined)
|
||||
? []
|
||||
: ValueType extends string
|
||||
? [string]
|
||||
: ValueType extends ReadonlyArray<unknown> // TODO: Use 'readonly unknown[]' in the next major version
|
||||
? ValueType
|
||||
: ValueType extends Iterable<infer T>
|
||||
? T[]
|
||||
: [ValueType];
|
||||
|
||||
export = arrify;
|
||||
@ -0,0 +1,23 @@
|
||||
'use strict';
|
||||
|
||||
const arrify = value => {
|
||||
if (value === null || value === undefined) {
|
||||
return [];
|
||||
}
|
||||
|
||||
if (Array.isArray(value)) {
|
||||
return value;
|
||||
}
|
||||
|
||||
if (typeof value === 'string') {
|
||||
return [value];
|
||||
}
|
||||
|
||||
if (typeof value[Symbol.iterator] === 'function') {
|
||||
return [...value];
|
||||
}
|
||||
|
||||
return [value];
|
||||
};
|
||||
|
||||
module.exports = arrify;
|
||||
@ -0,0 +1,9 @@
|
||||
MIT License
|
||||
|
||||
Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com)
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
@ -0,0 +1,35 @@
|
||||
{
|
||||
"name": "arrify",
|
||||
"version": "2.0.1",
|
||||
"description": "Convert a value to an array",
|
||||
"license": "MIT",
|
||||
"repository": "sindresorhus/arrify",
|
||||
"author": {
|
||||
"name": "Sindre Sorhus",
|
||||
"email": "sindresorhus@gmail.com",
|
||||
"url": "sindresorhus.com"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=8"
|
||||
},
|
||||
"scripts": {
|
||||
"test": "xo && ava && tsd"
|
||||
},
|
||||
"files": [
|
||||
"index.js",
|
||||
"index.d.ts"
|
||||
],
|
||||
"keywords": [
|
||||
"array",
|
||||
"arrify",
|
||||
"arrayify",
|
||||
"convert",
|
||||
"value",
|
||||
"ensure"
|
||||
],
|
||||
"devDependencies": {
|
||||
"ava": "^1.4.1",
|
||||
"tsd": "^0.7.2",
|
||||
"xo": "^0.24.0"
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,39 @@
|
||||
# arrify [](https://travis-ci.org/sindresorhus/arrify)
|
||||
|
||||
> Convert a value to an array
|
||||
|
||||
|
||||
## Install
|
||||
|
||||
```
|
||||
$ npm install arrify
|
||||
```
|
||||
|
||||
|
||||
## Usage
|
||||
|
||||
```js
|
||||
const arrify = require('arrify');
|
||||
|
||||
arrify('🦄');
|
||||
//=> ['🦄']
|
||||
|
||||
arrify(['🦄']);
|
||||
//=> ['🦄']
|
||||
|
||||
arrify(new Set(['🦄']));
|
||||
//=> ['🦄']
|
||||
|
||||
arrify(null);
|
||||
//=> []
|
||||
|
||||
arrify(undefined);
|
||||
//=> []
|
||||
```
|
||||
|
||||
*Supplying `null` or `undefined` results in an empty array.*
|
||||
|
||||
|
||||
## License
|
||||
|
||||
MIT © [Sindre Sorhus](https://sindresorhus.com)
|
||||
@ -0,0 +1,21 @@
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2021 Vercel, Inc.
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
@ -0,0 +1,53 @@
|
||||
# async-retry
|
||||
|
||||
Retrying made simple, easy, and async.
|
||||
|
||||
## Usage
|
||||
|
||||
```js
|
||||
// Packages
|
||||
const retry = require('async-retry');
|
||||
const fetch = require('node-fetch');
|
||||
|
||||
await retry(
|
||||
async (bail) => {
|
||||
// if anything throws, we retry
|
||||
const res = await fetch('https://google.com');
|
||||
|
||||
if (403 === res.status) {
|
||||
// don't retry upon 403
|
||||
bail(new Error('Unauthorized'));
|
||||
return;
|
||||
}
|
||||
|
||||
const data = await res.text();
|
||||
return data.substr(0, 500);
|
||||
},
|
||||
{
|
||||
retries: 5,
|
||||
}
|
||||
);
|
||||
```
|
||||
|
||||
### API
|
||||
|
||||
```js
|
||||
retry(retrier : Function, opts : Object) => Promise
|
||||
```
|
||||
|
||||
- The supplied function can be `async` or not. In other words, it can be a function that returns a `Promise` or a value.
|
||||
- The supplied function receives two parameters
|
||||
1. A `Function` you can invoke to abort the retrying (bail)
|
||||
2. A `Number` identifying the attempt. The absolute first attempt (before any retries) is `1`.
|
||||
- The `opts` are passed to `node-retry`. Read [its docs](https://github.com/tim-kos/node-retry)
|
||||
- `retries`: The maximum amount of times to retry the operation. Default is `10`.
|
||||
- `factor`: The exponential factor to use. Default is `2`.
|
||||
- `minTimeout`: The number of milliseconds before starting the first retry. Default is `1000`.
|
||||
- `maxTimeout`: The maximum number of milliseconds between two retries. Default is `Infinity`.
|
||||
- `randomize`: Randomizes the timeouts by multiplying with a factor between `1` to `2`. Default is `true`.
|
||||
- `onRetry`: an optional `Function` that is invoked after a new retry is performed. It's passed the `Error` that triggered it as a parameter.
|
||||
|
||||
## Authors
|
||||
|
||||
- Guillermo Rauch ([@rauchg](https://twitter.com/rauchg)) - [Vercel](https://vercel.com)
|
||||
- Leo Lamprecht ([@notquiteleo](https://twitter.com/notquiteleo)) - [Vercel](https://vercel.com)
|
||||
@ -0,0 +1,61 @@
|
||||
// Packages
|
||||
var retrier = require('retry');
|
||||
|
||||
function retry(fn, opts) {
|
||||
function run(resolve, reject) {
|
||||
var options = opts || {};
|
||||
var op;
|
||||
|
||||
// Default `randomize` to true
|
||||
if (!('randomize' in options)) {
|
||||
options.randomize = true;
|
||||
}
|
||||
|
||||
op = retrier.operation(options);
|
||||
|
||||
// We allow the user to abort retrying
|
||||
// this makes sense in the cases where
|
||||
// knowledge is obtained that retrying
|
||||
// would be futile (e.g.: auth errors)
|
||||
|
||||
function bail(err) {
|
||||
reject(err || new Error('Aborted'));
|
||||
}
|
||||
|
||||
function onError(err, num) {
|
||||
if (err.bail) {
|
||||
bail(err);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!op.retry(err)) {
|
||||
reject(op.mainError());
|
||||
} else if (options.onRetry) {
|
||||
options.onRetry(err, num);
|
||||
}
|
||||
}
|
||||
|
||||
function runAttempt(num) {
|
||||
var val;
|
||||
|
||||
try {
|
||||
val = fn(bail, num);
|
||||
} catch (err) {
|
||||
onError(err, num);
|
||||
return;
|
||||
}
|
||||
|
||||
Promise.resolve(val)
|
||||
.then(resolve)
|
||||
.catch(function catchIt(err) {
|
||||
onError(err, num);
|
||||
});
|
||||
}
|
||||
|
||||
op.attempt(runAttempt);
|
||||
}
|
||||
|
||||
return new Promise(run);
|
||||
}
|
||||
|
||||
module.exports = retry;
|
||||
@ -0,0 +1,55 @@
|
||||
{
|
||||
"name": "async-retry",
|
||||
"version": "1.3.3",
|
||||
"description": "Retrying made simple, easy and async",
|
||||
"main": "./lib/index.js",
|
||||
"scripts": {
|
||||
"test": "yarn run test-lint && yarn run test-unit",
|
||||
"test-lint": "eslint .",
|
||||
"test-unit": "ava",
|
||||
"lint:staged": "lint-staged"
|
||||
},
|
||||
"files": [
|
||||
"lib"
|
||||
],
|
||||
"license": "MIT",
|
||||
"repository": "vercel/async-retry",
|
||||
"ava": {
|
||||
"failFast": true
|
||||
},
|
||||
"dependencies": {
|
||||
"retry": "0.13.1"
|
||||
},
|
||||
"pre-commit": "lint:staged",
|
||||
"lint-staged": {
|
||||
"*.js": [
|
||||
"eslint",
|
||||
"prettier --write --single-quote",
|
||||
"git add"
|
||||
]
|
||||
},
|
||||
"eslintConfig": {
|
||||
"extends": [
|
||||
"airbnb",
|
||||
"prettier"
|
||||
],
|
||||
"rules": {
|
||||
"no-var": 0,
|
||||
"prefer-arrow-callback": 0
|
||||
}
|
||||
},
|
||||
"devDependencies": {
|
||||
"ava": "3.15.0",
|
||||
"eslint": "7.32.0",
|
||||
"eslint-config-airbnb": "18.2.1",
|
||||
"eslint-config-prettier": "8.3.0",
|
||||
"eslint-plugin-import": "2.24.0",
|
||||
"eslint-plugin-jsx-a11y": "6.4.1",
|
||||
"eslint-plugin-react": "7.24.0",
|
||||
"lint-staged": "11.1.2",
|
||||
"node-fetch": "2.6.1",
|
||||
"pre-commit": "1.2.2",
|
||||
"prettier": "2.3.2",
|
||||
"then-sleep": "1.0.1"
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,290 @@
|
||||
#### 9.1.1
|
||||
* 04/12/22
|
||||
* #338 [BUGFIX] `exponentiatedBy`: ensure `0**-n === Infinity` for very large `n`.
|
||||
|
||||
#### 9.1.0
|
||||
* 08/08/22
|
||||
* #329 Remove `import` example.
|
||||
* #277 Resolve lint warnings and add number `toString` note.
|
||||
* Correct `decimalPlaces()` return type in *bignumber.d.ts*.
|
||||
* Add ES module global `crypto` example.
|
||||
* #322 Add `exports` field to *package.json*.
|
||||
* #251 (#308) Amend *bignumber.d.ts* to allow instantiating a BigNumber without `new`.
|
||||
|
||||
#### 9.0.2
|
||||
* 12/12/21
|
||||
* #250 [BUGFIX] Allow use of user-defined alphabet for base 10.
|
||||
* #295 Remove *bignumber.min.js* and amend *README.md*.
|
||||
* Update *.travis.yml* and *LICENCE.md*.
|
||||
|
||||
#### 9.0.1
|
||||
* 28/09/20
|
||||
* [BUGFIX] #276 Correct `sqrt` initial estimate.
|
||||
* Update *.travis.yml*, *LICENCE.md* and *README.md*.
|
||||
|
||||
#### 9.0.0
|
||||
* 27/05/2019
|
||||
* For compatibility with legacy browsers, remove `Symbol` references.
|
||||
|
||||
#### 8.1.1
|
||||
* 24/02/2019
|
||||
* [BUGFIX] #222 Restore missing `var` to `export BigNumber`.
|
||||
* Allow any key in BigNumber.Instance in *bignumber.d.ts*.
|
||||
|
||||
#### 8.1.0
|
||||
* 23/02/2019
|
||||
* [NEW FEATURE] #220 Create a BigNumber using `{s, e, c}`.
|
||||
* [NEW FEATURE] `isBigNumber`: if `BigNumber.DEBUG` is `true`, also check that the BigNumber instance is well-formed.
|
||||
* Remove `instanceof` checks; just use `_isBigNumber` to identify a BigNumber instance.
|
||||
* Add `_isBigNumber` to prototype in *bignumber.mjs*.
|
||||
* Add tests for BigNumber creation from object.
|
||||
* Update *API.html*.
|
||||
|
||||
#### 8.0.2
|
||||
* 13/01/2019
|
||||
* #209 `toPrecision` without argument should follow `toString`.
|
||||
* Improve *Use* section of *README*.
|
||||
* Optimise `toString(10)`.
|
||||
* Add verson number to API doc.
|
||||
|
||||
#### 8.0.1
|
||||
* 01/11/2018
|
||||
* Rest parameter must be array type in *bignumber.d.ts*.
|
||||
|
||||
#### 8.0.0
|
||||
* 01/11/2018
|
||||
* [NEW FEATURE] Add `BigNumber.sum` method.
|
||||
* [NEW FEATURE]`toFormat`: add `prefix` and `suffix` options.
|
||||
* [NEW FEATURE] #178 Pass custom formatting to `toFormat`.
|
||||
* [BREAKING CHANGE] #184 `toFraction`: return array of BigNumbers not strings.
|
||||
* [NEW FEATURE] #185 Enable overwrite of `valueOf` to prevent accidental addition to string.
|
||||
* #183 Add Node.js `crypto` requirement to documentation.
|
||||
* [BREAKING CHANGE] #198 Disallow signs and whitespace in custom alphabet.
|
||||
* [NEW FEATURE] #188 Implement `util.inspect.custom` for Node.js REPL.
|
||||
* #170 Make `isBigNumber` a type guard in *bignumber.d.ts*.
|
||||
* [BREAKING CHANGE] `BigNumber.min` and `BigNumber.max`: don't accept an array.
|
||||
* Update *.travis.yml*.
|
||||
* Remove *bower.json*.
|
||||
|
||||
#### 7.2.1
|
||||
* 24/05/2018
|
||||
* Add `browser` field to *package.json*.
|
||||
|
||||
#### 7.2.0
|
||||
* 22/05/2018
|
||||
* #166 Correct *.mjs* file. Remove extension from `main` field in *package.json*.
|
||||
|
||||
#### 7.1.0
|
||||
* 18/05/2018
|
||||
* Add `module` field to *package.json* for *bignumber.mjs*.
|
||||
|
||||
#### 7.0.2
|
||||
* 17/05/2018
|
||||
* #165 Bugfix: upper-case letters for bases 11-36 in a custom alphabet.
|
||||
* Add note to *README* regarding creating BigNumbers from Number values.
|
||||
|
||||
#### 7.0.1
|
||||
* 26/04/2018
|
||||
* #158 Fix global object variable name typo.
|
||||
|
||||
#### 7.0.0
|
||||
* 26/04/2018
|
||||
* #143 Remove global BigNumber from typings.
|
||||
* #144 Enable compatibility with `Object.freeze(Object.prototype)`.
|
||||
* #148 #123 #11 Only throw on a number primitive with more than 15 significant digits if `BigNumber.DEBUG` is `true`.
|
||||
* Only throw on an invalid BigNumber value if `BigNumber.DEBUG` is `true`. Return BigNumber `NaN` instead.
|
||||
* #154 `exponentiatedBy`: allow BigNumber exponent.
|
||||
* #156 Prevent Content Security Policy *unsafe-eval* issue.
|
||||
* `toFraction`: allow `Infinity` maximum denominator.
|
||||
* Comment-out some excess tests to reduce test time.
|
||||
* Amend indentation and other spacing.
|
||||
|
||||
#### 6.0.0
|
||||
* 26/01/2018
|
||||
* #137 Implement `APLHABET` configuration option.
|
||||
* Remove `ERRORS` configuration option.
|
||||
* Remove `toDigits` method; extend `precision` method accordingly.
|
||||
* Remove s`round` method; extend `decimalPlaces` method accordingly.
|
||||
* Remove methods: `ceil`, `floor`, and `truncated`.
|
||||
* Remove method aliases: `add`, `cmp`, `isInt`, `isNeg`, `trunc`, `mul`, `neg` and `sub`.
|
||||
* Rename methods: `shift` to `shiftedBy`, `another` to `clone`, `toPower` to `exponentiatedBy`, and `equals` to `isEqualTo`.
|
||||
* Rename methods: add `is` prefix to `greaterThan`, `greaterThanOrEqualTo`, `lessThan` and `lessThanOrEqualTo`.
|
||||
* Add methods: `multipliedBy`, `isBigNumber`, `isPositive`, `integerValue`, `maximum` and `minimum`.
|
||||
* Refactor test suite.
|
||||
* Add *CHANGELOG.md*.
|
||||
* Rewrite *bignumber.d.ts*.
|
||||
* Redo API image.
|
||||
|
||||
#### 5.0.0
|
||||
* 27/11/2017
|
||||
* #81 Don't throw on constructor call without `new`.
|
||||
|
||||
#### 4.1.0
|
||||
* 26/09/2017
|
||||
* Remove node 0.6 from *.travis.yml*.
|
||||
* Add *bignumber.mjs*.
|
||||
|
||||
#### 4.0.4
|
||||
* 03/09/2017
|
||||
* Add missing aliases to *bignumber.d.ts*.
|
||||
|
||||
#### 4.0.3
|
||||
* 30/08/2017
|
||||
* Add types: *bignumber.d.ts*.
|
||||
|
||||
#### 4.0.2
|
||||
* 03/05/2017
|
||||
* #120 Workaround Safari/Webkit bug.
|
||||
|
||||
#### 4.0.1
|
||||
* 05/04/2017
|
||||
* #121 BigNumber.default to BigNumber['default'].
|
||||
|
||||
#### 4.0.0
|
||||
* 09/01/2017
|
||||
* Replace BigNumber.isBigNumber method with isBigNumber prototype property.
|
||||
|
||||
#### 3.1.2
|
||||
* 08/01/2017
|
||||
* Minor documentation edit.
|
||||
|
||||
#### 3.1.1
|
||||
* 08/01/2017
|
||||
* Uncomment `isBigNumber` tests.
|
||||
* Ignore dot files.
|
||||
|
||||
#### 3.1.0
|
||||
* 08/01/2017
|
||||
* Add `isBigNumber` method.
|
||||
|
||||
#### 3.0.2
|
||||
* 08/01/2017
|
||||
* Bugfix: Possible incorrect value of `ERRORS` after a `BigNumber.another` call (due to `parseNumeric` declaration in outer scope).
|
||||
|
||||
#### 3.0.1
|
||||
* 23/11/2016
|
||||
* Apply fix for old ipads with `%` issue, see #57 and #102.
|
||||
* Correct error message.
|
||||
|
||||
#### 3.0.0
|
||||
* 09/11/2016
|
||||
* Remove `require('crypto')` - leave it to the user.
|
||||
* Add `BigNumber.set` as `BigNumber.config` alias.
|
||||
* Default `POW_PRECISION` to `0`.
|
||||
|
||||
#### 2.4.0
|
||||
* 14/07/2016
|
||||
* #97 Add exports to support ES6 imports.
|
||||
|
||||
#### 2.3.0
|
||||
* 07/03/2016
|
||||
* #86 Add modulus parameter to `toPower`.
|
||||
|
||||
#### 2.2.0
|
||||
* 03/03/2016
|
||||
* #91 Permit larger JS integers.
|
||||
|
||||
#### 2.1.4
|
||||
* 15/12/2015
|
||||
* Correct UMD.
|
||||
|
||||
#### 2.1.3
|
||||
* 13/12/2015
|
||||
* Refactor re global object and crypto availability when bundling.
|
||||
|
||||
#### 2.1.2
|
||||
* 10/12/2015
|
||||
* Bugfix: `window.crypto` not assigned to `crypto`.
|
||||
|
||||
#### 2.1.1
|
||||
* 09/12/2015
|
||||
* Prevent code bundler from adding `crypto` shim.
|
||||
|
||||
#### 2.1.0
|
||||
* 26/10/2015
|
||||
* For `valueOf` and `toJSON`, include the minus sign with negative zero.
|
||||
|
||||
#### 2.0.8
|
||||
* 2/10/2015
|
||||
* Internal round function bugfix.
|
||||
|
||||
#### 2.0.6
|
||||
* 31/03/2015
|
||||
* Add bower.json. Tweak division after in-depth review.
|
||||
|
||||
#### 2.0.5
|
||||
* 25/03/2015
|
||||
* Amend README. Remove bitcoin address.
|
||||
|
||||
#### 2.0.4
|
||||
* 25/03/2015
|
||||
* Critical bugfix #58: division.
|
||||
|
||||
#### 2.0.3
|
||||
* 18/02/2015
|
||||
* Amend README. Add source map.
|
||||
|
||||
#### 2.0.2
|
||||
* 18/02/2015
|
||||
* Correct links.
|
||||
|
||||
#### 2.0.1
|
||||
* 18/02/2015
|
||||
* Add `max`, `min`, `precision`, `random`, `shiftedBy`, `toDigits` and `truncated` methods.
|
||||
* Add the short-forms: `add`, `mul`, `sd`, `sub` and `trunc`.
|
||||
* Add an `another` method to enable multiple independent constructors to be created.
|
||||
* Add support for the base 2, 8 and 16 prefixes `0b`, `0o` and `0x`.
|
||||
* Enable a rounding mode to be specified as a second parameter to `toExponential`, `toFixed`, `toFormat` and `toPrecision`.
|
||||
* Add a `CRYPTO` configuration property so cryptographically-secure pseudo-random number generation can be specified.
|
||||
* Add a `MODULO_MODE` configuration property to enable the rounding mode used by the `modulo` operation to be specified.
|
||||
* Add a `POW_PRECISION` configuration property to enable the number of significant digits calculated by the power operation to be limited.
|
||||
* Improve code quality.
|
||||
* Improve documentation.
|
||||
|
||||
#### 2.0.0
|
||||
* 29/12/2014
|
||||
* Add `dividedToIntegerBy`, `isInteger` and `toFormat` methods.
|
||||
* Remove the following short-forms: `isF`, `isZ`, `toE`, `toF`, `toFr`, `toN`, `toP`, `toS`.
|
||||
* Store a BigNumber's coefficient in base 1e14, rather than base 10.
|
||||
* Add fast path for integers to BigNumber constructor.
|
||||
* Incorporate the library into the online documentation.
|
||||
|
||||
#### 1.5.0
|
||||
* 13/11/2014
|
||||
* Add `toJSON` and `decimalPlaces` methods.
|
||||
|
||||
#### 1.4.1
|
||||
* 08/06/2014
|
||||
* Amend README.
|
||||
|
||||
#### 1.4.0
|
||||
* 08/05/2014
|
||||
* Add `toNumber`.
|
||||
|
||||
#### 1.3.0
|
||||
* 08/11/2013
|
||||
* Ensure correct rounding of `sqrt` in all, rather than almost all, cases.
|
||||
* Maximum radix to 64.
|
||||
|
||||
#### 1.2.1
|
||||
* 17/10/2013
|
||||
* Sign of zero when x < 0 and x + (-x) = 0.
|
||||
|
||||
#### 1.2.0
|
||||
* 19/9/2013
|
||||
* Throw Error objects for stack.
|
||||
|
||||
#### 1.1.1
|
||||
* 22/8/2013
|
||||
* Show original value in constructor error message.
|
||||
|
||||
#### 1.1.0
|
||||
* 1/8/2013
|
||||
* Allow numbers with trailing radix point.
|
||||
|
||||
#### 1.0.1
|
||||
* Bugfix: error messages with incorrect method name
|
||||
|
||||
#### 1.0.0
|
||||
* 8/11/2012
|
||||
* Initial release
|
||||
@ -0,0 +1,26 @@
|
||||
The MIT License (MIT)
|
||||
=====================
|
||||
|
||||
Copyright © `<2022>` `Michael Mclaughlin`
|
||||
|
||||
Permission is hereby granted, free of charge, to any person
|
||||
obtaining a copy of this software and associated documentation
|
||||
files (the “Software”), to deal in the Software without
|
||||
restriction, including without limitation the rights to use,
|
||||
copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the
|
||||
Software is furnished to do so, subject to the following
|
||||
conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be
|
||||
included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED “AS IS”, WITHOUT WARRANTY OF ANY KIND,
|
||||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
||||
OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
||||
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
||||
HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
||||
OTHER DEALINGS IN THE SOFTWARE.
|
||||
|
||||
@ -0,0 +1,286 @@
|
||||

|
||||
|
||||
A JavaScript library for arbitrary-precision decimal and non-decimal arithmetic.
|
||||
|
||||
[](https://www.npmjs.com/package/bignumber.js)
|
||||
[](https://www.npmjs.com/package/bignumber.js)
|
||||
|
||||
<br />
|
||||
|
||||
## Features
|
||||
|
||||
- Integers and decimals
|
||||
- Simple API but full-featured
|
||||
- Faster, smaller, and perhaps easier to use than JavaScript versions of Java's BigDecimal
|
||||
- 8 KB minified and gzipped
|
||||
- Replicates the `toExponential`, `toFixed`, `toPrecision` and `toString` methods of JavaScript's Number type
|
||||
- Includes a `toFraction` and a correctly-rounded `squareRoot` method
|
||||
- Supports cryptographically-secure pseudo-random number generation
|
||||
- No dependencies
|
||||
- Wide platform compatibility: uses JavaScript 1.5 (ECMAScript 3) features only
|
||||
- Comprehensive [documentation](http://mikemcl.github.io/bignumber.js/) and test set
|
||||
|
||||

|
||||
|
||||
If a smaller and simpler library is required see [big.js](https://github.com/MikeMcl/big.js/).
|
||||
It's less than half the size but only works with decimal numbers and only has half the methods.
|
||||
It also has fewer configuration options than this library, and does not allow `NaN` or `Infinity`.
|
||||
|
||||
See also [decimal.js](https://github.com/MikeMcl/decimal.js/), which among other things adds support for non-integer powers, and performs all operations to a specified number of significant digits.
|
||||
|
||||
## Load
|
||||
|
||||
The library is the single JavaScript file *bignumber.js* or ES module *bignumber.mjs*.
|
||||
|
||||
### Browser
|
||||
|
||||
```html
|
||||
<script src='path/to/bignumber.js'></script>
|
||||
```
|
||||
|
||||
> ES module
|
||||
|
||||
```html
|
||||
<script type="module">
|
||||
import BigNumber from './path/to/bignumber.mjs';
|
||||
```
|
||||
|
||||
> Get a minified version from a CDN:
|
||||
|
||||
```html
|
||||
<script src='https://cdn.jsdelivr.net/npm/bignumber.js@9.1.0/bignumber.min.js'></script>
|
||||
```
|
||||
|
||||
### [Node.js](http://nodejs.org)
|
||||
|
||||
```bash
|
||||
npm install bignumber.js
|
||||
```
|
||||
|
||||
```javascript
|
||||
const BigNumber = require('bignumber.js');
|
||||
```
|
||||
|
||||
> ES module
|
||||
|
||||
```javascript
|
||||
import BigNumber from "bignumber.js";
|
||||
import { BigNumber } from "./node_modules/bignumber.js/bignumber.mjs";
|
||||
```
|
||||
|
||||
### [Deno](https://deno.land/)
|
||||
|
||||
```javascript
|
||||
import BigNumber from 'https://raw.githubusercontent.com/mikemcl/bignumber.js/v9.1.0/bignumber.mjs';
|
||||
import BigNumber from 'https://unpkg.com/bignumber.js@latest/bignumber.mjs';
|
||||
```
|
||||
|
||||
## Use
|
||||
|
||||
The library exports a single constructor function, [`BigNumber`](http://mikemcl.github.io/bignumber.js/#bignumber), which accepts a value of type Number, String or BigNumber,
|
||||
|
||||
```javascript
|
||||
let x = new BigNumber(123.4567);
|
||||
let y = BigNumber('123456.7e-3');
|
||||
let z = new BigNumber(x);
|
||||
x.isEqualTo(y) && y.isEqualTo(z) && x.isEqualTo(z); // true
|
||||
```
|
||||
|
||||
To get the string value of a BigNumber use [`toString()`](http://mikemcl.github.io/bignumber.js/#toS) or [`toFixed()`](http://mikemcl.github.io/bignumber.js/#toFix). Using `toFixed()` prevents exponential notation being returned, no matter how large or small the value.
|
||||
|
||||
```javascript
|
||||
let x = new BigNumber('1111222233334444555566');
|
||||
x.toString(); // "1.111222233334444555566e+21"
|
||||
x.toFixed(); // "1111222233334444555566"
|
||||
```
|
||||
|
||||
If the limited precision of Number values is not well understood, it is recommended to create BigNumbers from String values rather than Number values to avoid a potential loss of precision.
|
||||
|
||||
*In all further examples below, `let`, semicolons and `toString` calls are not shown. If a commented-out value is in quotes it means `toString` has been called on the preceding expression.*
|
||||
|
||||
```javascript
|
||||
// Precision loss from using numeric literals with more than 15 significant digits.
|
||||
new BigNumber(1.0000000000000001) // '1'
|
||||
new BigNumber(88259496234518.57) // '88259496234518.56'
|
||||
new BigNumber(99999999999999999999) // '100000000000000000000'
|
||||
|
||||
// Precision loss from using numeric literals outside the range of Number values.
|
||||
new BigNumber(2e+308) // 'Infinity'
|
||||
new BigNumber(1e-324) // '0'
|
||||
|
||||
// Precision loss from the unexpected result of arithmetic with Number values.
|
||||
new BigNumber(0.7 + 0.1) // '0.7999999999999999'
|
||||
```
|
||||
|
||||
When creating a BigNumber from a Number, note that a BigNumber is created from a Number's decimal `toString()` value not from its underlying binary value. If the latter is required, then pass the Number's `toString(2)` value and specify base 2.
|
||||
|
||||
```javascript
|
||||
new BigNumber(Number.MAX_VALUE.toString(2), 2)
|
||||
```
|
||||
|
||||
BigNumbers can be created from values in bases from 2 to 36. See [`ALPHABET`](http://mikemcl.github.io/bignumber.js/#alphabet) to extend this range.
|
||||
|
||||
```javascript
|
||||
a = new BigNumber(1011, 2) // "11"
|
||||
b = new BigNumber('zz.9', 36) // "1295.25"
|
||||
c = a.plus(b) // "1306.25"
|
||||
```
|
||||
|
||||
*Performance is better if base 10 is NOT specified for decimal values. Only specify base 10 when you want to limit the number of decimal places of the input value to the current [`DECIMAL_PLACES`](http://mikemcl.github.io/bignumber.js/#decimal-places) setting.*
|
||||
|
||||
A BigNumber is immutable in the sense that it is not changed by its methods.
|
||||
|
||||
```javascript
|
||||
0.3 - 0.1 // 0.19999999999999998
|
||||
x = new BigNumber(0.3)
|
||||
x.minus(0.1) // "0.2"
|
||||
x // "0.3"
|
||||
```
|
||||
|
||||
The methods that return a BigNumber can be chained.
|
||||
|
||||
```javascript
|
||||
x.dividedBy(y).plus(z).times(9)
|
||||
x.times('1.23456780123456789e+9').plus(9876.5432321).dividedBy('4444562598.111772').integerValue()
|
||||
```
|
||||
|
||||
Some of the longer method names have a shorter alias.
|
||||
|
||||
```javascript
|
||||
x.squareRoot().dividedBy(y).exponentiatedBy(3).isEqualTo(x.sqrt().div(y).pow(3)) // true
|
||||
x.modulo(y).multipliedBy(z).eq(x.mod(y).times(z)) // true
|
||||
```
|
||||
|
||||
As with JavaScript's Number type, there are [`toExponential`](http://mikemcl.github.io/bignumber.js/#toE), [`toFixed`](http://mikemcl.github.io/bignumber.js/#toFix) and [`toPrecision`](http://mikemcl.github.io/bignumber.js/#toP) methods.
|
||||
|
||||
```javascript
|
||||
x = new BigNumber(255.5)
|
||||
x.toExponential(5) // "2.55500e+2"
|
||||
x.toFixed(5) // "255.50000"
|
||||
x.toPrecision(5) // "255.50"
|
||||
x.toNumber() // 255.5
|
||||
```
|
||||
|
||||
A base can be specified for [`toString`](http://mikemcl.github.io/bignumber.js/#toS).
|
||||
|
||||
*Performance is better if base 10 is NOT specified, i.e. use `toString()` not `toString(10)`. Only specify base 10 when you want to limit the number of decimal places of the string to the current [`DECIMAL_PLACES`](http://mikemcl.github.io/bignumber.js/#decimal-places) setting.*
|
||||
|
||||
```javascript
|
||||
x.toString(16) // "ff.8"
|
||||
```
|
||||
|
||||
There is a [`toFormat`](http://mikemcl.github.io/bignumber.js/#toFor) method which may be useful for internationalisation.
|
||||
|
||||
```javascript
|
||||
y = new BigNumber('1234567.898765')
|
||||
y.toFormat(2) // "1,234,567.90"
|
||||
```
|
||||
|
||||
The maximum number of decimal places of the result of an operation involving division (i.e. a division, square root, base conversion or negative power operation) is set using the `set` or `config` method of the `BigNumber` constructor.
|
||||
|
||||
The other arithmetic operations always give the exact result.
|
||||
|
||||
```javascript
|
||||
BigNumber.set({ DECIMAL_PLACES: 10, ROUNDING_MODE: 4 })
|
||||
|
||||
x = new BigNumber(2)
|
||||
y = new BigNumber(3)
|
||||
z = x.dividedBy(y) // "0.6666666667"
|
||||
z.squareRoot() // "0.8164965809"
|
||||
z.exponentiatedBy(-3) // "3.3749999995"
|
||||
z.toString(2) // "0.1010101011"
|
||||
z.multipliedBy(z) // "0.44444444448888888889"
|
||||
z.multipliedBy(z).decimalPlaces(10) // "0.4444444445"
|
||||
```
|
||||
|
||||
There is a [`toFraction`](http://mikemcl.github.io/bignumber.js/#toFr) method with an optional *maximum denominator* argument
|
||||
|
||||
```javascript
|
||||
y = new BigNumber(355)
|
||||
pi = y.dividedBy(113) // "3.1415929204"
|
||||
pi.toFraction() // [ "7853982301", "2500000000" ]
|
||||
pi.toFraction(1000) // [ "355", "113" ]
|
||||
```
|
||||
|
||||
and [`isNaN`](http://mikemcl.github.io/bignumber.js/#isNaN) and [`isFinite`](http://mikemcl.github.io/bignumber.js/#isF) methods, as `NaN` and `Infinity` are valid `BigNumber` values.
|
||||
|
||||
```javascript
|
||||
x = new BigNumber(NaN) // "NaN"
|
||||
y = new BigNumber(Infinity) // "Infinity"
|
||||
x.isNaN() && !y.isNaN() && !x.isFinite() && !y.isFinite() // true
|
||||
```
|
||||
|
||||
The value of a BigNumber is stored in a decimal floating point format in terms of a coefficient, exponent and sign.
|
||||
|
||||
```javascript
|
||||
x = new BigNumber(-123.456);
|
||||
x.c // [ 123, 45600000000000 ] coefficient (i.e. significand)
|
||||
x.e // 2 exponent
|
||||
x.s // -1 sign
|
||||
```
|
||||
|
||||
For advanced usage, multiple BigNumber constructors can be created, each with its own independent configuration.
|
||||
|
||||
```javascript
|
||||
// Set DECIMAL_PLACES for the original BigNumber constructor
|
||||
BigNumber.set({ DECIMAL_PLACES: 10 })
|
||||
|
||||
// Create another BigNumber constructor, optionally passing in a configuration object
|
||||
BN = BigNumber.clone({ DECIMAL_PLACES: 5 })
|
||||
|
||||
x = new BigNumber(1)
|
||||
y = new BN(1)
|
||||
|
||||
x.div(3) // '0.3333333333'
|
||||
y.div(3) // '0.33333'
|
||||
```
|
||||
|
||||
To avoid having to call `toString` or `valueOf` on a BigNumber to get its value in the Node.js REPL or when using `console.log` use
|
||||
|
||||
```javascript
|
||||
BigNumber.prototype[require('util').inspect.custom] = BigNumber.prototype.valueOf;
|
||||
```
|
||||
|
||||
For further information see the [API](http://mikemcl.github.io/bignumber.js/) reference in the *doc* directory.
|
||||
|
||||
## Test
|
||||
|
||||
The *test/modules* directory contains the test scripts for each method.
|
||||
|
||||
The tests can be run with Node.js or a browser. For Node.js use
|
||||
|
||||
```bash
|
||||
npm test
|
||||
```
|
||||
|
||||
or
|
||||
|
||||
```bash
|
||||
node test/test
|
||||
```
|
||||
|
||||
To test a single method, use, for example
|
||||
|
||||
```bash
|
||||
node test/methods/toFraction
|
||||
```
|
||||
|
||||
For the browser, open *test/test.html*.
|
||||
|
||||
## Minify
|
||||
|
||||
To minify using, for example, [terser](https://github.com/terser/terser)
|
||||
|
||||
```bash
|
||||
npm install -g terser
|
||||
```
|
||||
|
||||
```bash
|
||||
terser big.js -c -m -o big.min.js
|
||||
```
|
||||
|
||||
## Licence
|
||||
|
||||
The MIT Licence.
|
||||
|
||||
See [LICENCE](https://github.com/MikeMcl/bignumber.js/blob/master/LICENCE).
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,50 @@
|
||||
{
|
||||
"name": "bignumber.js",
|
||||
"description": "A library for arbitrary-precision decimal and non-decimal arithmetic",
|
||||
"version": "9.1.1",
|
||||
"keywords": [
|
||||
"arbitrary",
|
||||
"precision",
|
||||
"arithmetic",
|
||||
"big",
|
||||
"number",
|
||||
"decimal",
|
||||
"float",
|
||||
"biginteger",
|
||||
"bigdecimal",
|
||||
"bignumber",
|
||||
"bigint",
|
||||
"bignum"
|
||||
],
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/MikeMcl/bignumber.js.git"
|
||||
},
|
||||
"main": "bignumber",
|
||||
"module": "bignumber.mjs",
|
||||
"browser": "bignumber.js",
|
||||
"types": "bignumber.d.ts",
|
||||
"exports": {
|
||||
".": {
|
||||
"types": "./bignumber.d.ts",
|
||||
"require": "./bignumber.js",
|
||||
"import": "./bignumber.mjs",
|
||||
"browser": "./bignumber.js"
|
||||
},
|
||||
"./bignumber.mjs": "./bignumber.mjs",
|
||||
"./bignumber.js": "./bignumber.js",
|
||||
"./package.json": "./package.json"
|
||||
},
|
||||
"author": {
|
||||
"name": "Michael Mclaughlin",
|
||||
"email": "M8ch88l@gmail.com"
|
||||
},
|
||||
"engines": {
|
||||
"node": "*"
|
||||
},
|
||||
"license": "MIT",
|
||||
"scripts": {
|
||||
"test": "node test/test"
|
||||
},
|
||||
"dependencies": {}
|
||||
}
|
||||
@ -0,0 +1,111 @@
|
||||
2.0.18 / 2020-01-05
|
||||
===================
|
||||
|
||||
* deps: mime-db@'>= 1.43.0 < 2'
|
||||
- Mark `font/ttf` as compressible
|
||||
- Remove compressible from `multipart/mixed`
|
||||
|
||||
2.0.17 / 2019-04-24
|
||||
===================
|
||||
|
||||
* deps: mime-db@'>= 1.40.0 < 2'
|
||||
|
||||
2.0.16 / 2019-02-18
|
||||
===================
|
||||
|
||||
* deps: mime-db@'>= 1.38.0 < 2'
|
||||
- Mark `text/less` as compressible
|
||||
|
||||
2.0.15 / 2018-09-17
|
||||
===================
|
||||
|
||||
* deps: mime-db@'>= 1.36.0 < 2'
|
||||
|
||||
2.0.14 / 2018-06-05
|
||||
===================
|
||||
|
||||
* deps: mime-db@'>= 1.34.0 < 2'
|
||||
- Mark all XML-derived types as compressible
|
||||
|
||||
2.0.13 / 2018-02-17
|
||||
===================
|
||||
|
||||
* deps: mime-db@'>= 1.33.0 < 2'
|
||||
|
||||
2.0.12 / 2017-10-20
|
||||
===================
|
||||
|
||||
* deps: mime-db@'>= 1.30.0 < 2'
|
||||
|
||||
2.0.11 / 2017-07-27
|
||||
===================
|
||||
|
||||
* deps: mime-db@'>= 1.29.0 < 2'
|
||||
|
||||
2.0.10 / 2017-03-23
|
||||
===================
|
||||
|
||||
* deps: mime-db@'>= 1.27.0 < 2'
|
||||
|
||||
2.0.9 / 2016-10-31
|
||||
==================
|
||||
|
||||
* Fix regex fallback to not override `compressible: false` in db
|
||||
* deps: mime-db@'>= 1.24.0 < 2'
|
||||
|
||||
2.0.8 / 2016-05-12
|
||||
==================
|
||||
|
||||
* deps: mime-db@'>= 1.23.0 < 2'
|
||||
|
||||
2.0.7 / 2016-01-18
|
||||
==================
|
||||
|
||||
* deps: mime-db@'>= 1.21.0 < 2'
|
||||
|
||||
2.0.6 / 2015-09-29
|
||||
==================
|
||||
|
||||
* deps: mime-db@'>= 1.19.0 < 2'
|
||||
|
||||
2.0.5 / 2015-07-30
|
||||
==================
|
||||
|
||||
* deps: mime-db@'>= 1.16.0 < 2'
|
||||
|
||||
2.0.4 / 2015-07-01
|
||||
==================
|
||||
|
||||
* deps: mime-db@'>= 1.14.0 < 2'
|
||||
* perf: enable strict mode
|
||||
|
||||
2.0.3 / 2015-06-08
|
||||
==================
|
||||
|
||||
* Fix regex fallback to work if type exists, but is undefined
|
||||
* perf: hoist regex declaration
|
||||
* perf: use regex to extract mime
|
||||
* deps: mime-db@'>= 1.13.0 < 2'
|
||||
|
||||
2.0.2 / 2015-01-31
|
||||
==================
|
||||
|
||||
* deps: mime-db@'>= 1.1.2 < 2'
|
||||
|
||||
2.0.1 / 2014-09-28
|
||||
==================
|
||||
|
||||
* deps: mime-db@1.x
|
||||
- Add new mime types
|
||||
- Add additional compressible
|
||||
- Update charsets
|
||||
|
||||
|
||||
2.0.0 / 2014-09-02
|
||||
==================
|
||||
|
||||
* use mime-db
|
||||
* remove .get()
|
||||
* specifications are now private
|
||||
* regex is now private
|
||||
* stricter regex
|
||||
@ -0,0 +1,24 @@
|
||||
(The MIT License)
|
||||
|
||||
Copyright (c) 2013 Jonathan Ong <me@jongleberry.com>
|
||||
Copyright (c) 2014 Jeremiah Senkpiel <fishrock123@rocketmail.com>
|
||||
Copyright (c) 2015 Douglas Christopher Wilson <doug@somethingdoug.com>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining
|
||||
a copy of this software and associated documentation files (the
|
||||
'Software'), to deal in the Software without restriction, including
|
||||
without limitation the rights to use, copy, modify, merge, publish,
|
||||
distribute, sublicense, and/or sell copies of the Software, and to
|
||||
permit persons to whom the Software is furnished to do so, subject to
|
||||
the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be
|
||||
included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND,
|
||||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
||||
IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
|
||||
CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
|
||||
TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
|
||||
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
@ -0,0 +1,61 @@
|
||||
# compressible
|
||||
|
||||
[![NPM Version][npm-version-image]][npm-url]
|
||||
[![NPM Downloads][npm-downloads-image]][npm-url]
|
||||
[![Node.js Version][node-version-image]][node-version-url]
|
||||
[![Build Status][travis-image]][travis-url]
|
||||
[![Test Coverage][coveralls-image]][coveralls-url]
|
||||
|
||||
Compressible `Content-Type` / `mime` checking.
|
||||
|
||||
## Installation
|
||||
|
||||
```sh
|
||||
$ npm install compressible
|
||||
```
|
||||
|
||||
## API
|
||||
|
||||
<!-- eslint-disable no-unused-vars -->
|
||||
|
||||
```js
|
||||
var compressible = require('compressible')
|
||||
```
|
||||
|
||||
### compressible(type)
|
||||
|
||||
Checks if the given `Content-Type` is compressible. The `type` argument is expected
|
||||
to be a value MIME type or `Content-Type` string, though no validation is performed.
|
||||
|
||||
The MIME is looked up in the [`mime-db`](https://www.npmjs.com/package/mime-db) and
|
||||
if there is compressible information in the database entry, that is returned. Otherwise,
|
||||
this module will fallback to `true` for the following types:
|
||||
|
||||
* `text/*`
|
||||
* `*/*+json`
|
||||
* `*/*+text`
|
||||
* `*/*+xml`
|
||||
|
||||
If this module is not sure if a type is specifically compressible or specifically
|
||||
uncompressible, `undefined` is returned.
|
||||
|
||||
<!-- eslint-disable no-undef -->
|
||||
|
||||
```js
|
||||
compressible('text/html') // => true
|
||||
compressible('image/png') // => false
|
||||
```
|
||||
|
||||
## License
|
||||
|
||||
[MIT](LICENSE)
|
||||
|
||||
[coveralls-image]: https://badgen.net/coveralls/c/github/jshttp/compressible/master
|
||||
[coveralls-url]: https://coveralls.io/r/jshttp/compressible?branch=master
|
||||
[node-version-image]: https://badgen.net/npm/node/compressible
|
||||
[node-version-url]: https://nodejs.org/en/download
|
||||
[npm-downloads-image]: https://badgen.net/npm/dm/compressible
|
||||
[npm-url]: https://npmjs.org/package/compressible
|
||||
[npm-version-image]: https://badgen.net/npm/v/compressible
|
||||
[travis-image]: https://badgen.net/travis/jshttp/compressible/master
|
||||
[travis-url]: https://travis-ci.org/jshttp/compressible
|
||||
@ -0,0 +1,58 @@
|
||||
/*!
|
||||
* compressible
|
||||
* Copyright(c) 2013 Jonathan Ong
|
||||
* Copyright(c) 2014 Jeremiah Senkpiel
|
||||
* Copyright(c) 2015 Douglas Christopher Wilson
|
||||
* MIT Licensed
|
||||
*/
|
||||
|
||||
'use strict'
|
||||
|
||||
/**
|
||||
* Module dependencies.
|
||||
* @private
|
||||
*/
|
||||
|
||||
var db = require('mime-db')
|
||||
|
||||
/**
|
||||
* Module variables.
|
||||
* @private
|
||||
*/
|
||||
|
||||
var COMPRESSIBLE_TYPE_REGEXP = /^text\/|\+(?:json|text|xml)$/i
|
||||
var EXTRACT_TYPE_REGEXP = /^\s*([^;\s]*)(?:;|\s|$)/
|
||||
|
||||
/**
|
||||
* Module exports.
|
||||
* @public
|
||||
*/
|
||||
|
||||
module.exports = compressible
|
||||
|
||||
/**
|
||||
* Checks if a type is compressible.
|
||||
*
|
||||
* @param {string} type
|
||||
* @return {Boolean} compressible
|
||||
* @public
|
||||
*/
|
||||
|
||||
function compressible (type) {
|
||||
if (!type || typeof type !== 'string') {
|
||||
return false
|
||||
}
|
||||
|
||||
// strip parameters
|
||||
var match = EXTRACT_TYPE_REGEXP.exec(type)
|
||||
var mime = match && match[1].toLowerCase()
|
||||
var data = db[mime]
|
||||
|
||||
// return database information
|
||||
if (data && data.compressible !== undefined) {
|
||||
return data.compressible
|
||||
}
|
||||
|
||||
// fallback to regexp or unknown
|
||||
return COMPRESSIBLE_TYPE_REGEXP.test(mime) || undefined
|
||||
}
|
||||
@ -0,0 +1,48 @@
|
||||
{
|
||||
"name": "compressible",
|
||||
"description": "Compressible Content-Type / mime checking",
|
||||
"version": "2.0.18",
|
||||
"contributors": [
|
||||
"Douglas Christopher Wilson <doug@somethingdoug.com>",
|
||||
"Jonathan Ong <me@jongleberry.com> (http://jongleberry.com)",
|
||||
"Jeremiah Senkpiel <fishrock123@rocketmail.com> (https://searchbeam.jit.su)"
|
||||
],
|
||||
"license": "MIT",
|
||||
"repository": "jshttp/compressible",
|
||||
"keywords": [
|
||||
"compress",
|
||||
"gzip",
|
||||
"mime",
|
||||
"content-type"
|
||||
],
|
||||
"dependencies": {
|
||||
"mime-db": ">= 1.43.0 < 2"
|
||||
},
|
||||
"devDependencies": {
|
||||
"eslint": "6.8.0",
|
||||
"eslint-config-standard": "14.1.0",
|
||||
"eslint-plugin-import": "2.19.1",
|
||||
"eslint-plugin-markdown": "1.0.1",
|
||||
"eslint-plugin-node": "11.0.0",
|
||||
"eslint-plugin-promise": "4.2.1",
|
||||
"eslint-plugin-standard": "4.0.1",
|
||||
"mocha": "7.0.0",
|
||||
"nyc": "15.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">= 0.6"
|
||||
},
|
||||
"files": [
|
||||
"HISTORY.md",
|
||||
"LICENSE",
|
||||
"README.md",
|
||||
"index.js"
|
||||
],
|
||||
"scripts": {
|
||||
"lint": "eslint --plugin markdown --ext js,md .",
|
||||
"test": "mocha --reporter spec --bail --check-leaks test/",
|
||||
"test-cov": "nyc --reporter=html --reporter=text npm test",
|
||||
"test-travis": "nyc --reporter=text npm test",
|
||||
"version": "node scripts/version-history.js && git add HISTORY.md"
|
||||
}
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in new issue