| [62b2964] | 1 | # pg-cloudflare
|
|---|
| 2 |
|
|---|
| 3 | `pg-cloudflare` makes it easier to take an existing package that relies on `tls` and `net`, and make it work in environments where only `connect()` is supported, such as Cloudflare Workers.
|
|---|
| 4 |
|
|---|
| 5 | `pg-cloudflare` wraps `connect()`, the [TCP Socket API](https://github.com/wintercg/proposal-sockets-api) proposed within WinterCG, and implemented in [Cloudflare Workers](https://developers.cloudflare.com/workers/runtime-apis/tcp-sockets/), and exposes an interface with methods similar to what the `net` and `tls` modules in Node.js expose. (ex: `net.connect(path[, options][, callback])`). This minimizes the number of changes needed in order to make an existing package work across JavaScript runtimes.
|
|---|
| 6 |
|
|---|
| 7 | ## Installation
|
|---|
| 8 |
|
|---|
| 9 | ```
|
|---|
| 10 | npm i --save-dev pg-cloudflare
|
|---|
| 11 | ```
|
|---|
| 12 |
|
|---|
| 13 | The package uses conditional exports to support bundlers that don't know about
|
|---|
| 14 | `cloudflare:sockets`, so the consumer code by default imports an empty file. To
|
|---|
| 15 | enable the package, resolve to the `cloudflare` condition in your bundler's
|
|---|
| 16 | config. For example:
|
|---|
| 17 |
|
|---|
| 18 | - `webpack.config.js`
|
|---|
| 19 | ```js
|
|---|
| 20 | export default {
|
|---|
| 21 | ...,
|
|---|
| 22 | resolve: { conditionNames: [..., "workerd"] },
|
|---|
| 23 | plugins: [
|
|---|
| 24 | // ignore cloudflare:sockets imports
|
|---|
| 25 | new webpack.IgnorePlugin({
|
|---|
| 26 | resourceRegExp: /^cloudflare:sockets$/,
|
|---|
| 27 | }),
|
|---|
| 28 | ],
|
|---|
| 29 | }
|
|---|
| 30 | ```
|
|---|
| 31 | - `vite.config.js`
|
|---|
| 32 |
|
|---|
| 33 | > [!NOTE]
|
|---|
| 34 | > If you are using the [Cloudflare Vite plugin](https://www.npmjs.com/package/@cloudflare/vite-plugin) then the following configuration is not necessary.
|
|---|
| 35 |
|
|---|
| 36 | ```js
|
|---|
| 37 | export default defineConfig({
|
|---|
| 38 | ...,
|
|---|
| 39 | resolve: {
|
|---|
| 40 | conditions: [..., "workerd"],
|
|---|
| 41 | },
|
|---|
| 42 | build: {
|
|---|
| 43 | ...,
|
|---|
| 44 | // don't try to bundle cloudflare:sockets
|
|---|
| 45 | rollupOptions: {
|
|---|
| 46 | external: [..., 'cloudflare:sockets'],
|
|---|
| 47 | },
|
|---|
| 48 | },
|
|---|
| 49 | })
|
|---|
| 50 | ```
|
|---|
| 51 |
|
|---|
| 52 | - `rollup.config.js`
|
|---|
| 53 | ```js
|
|---|
| 54 | export default defineConfig({
|
|---|
| 55 | ...,
|
|---|
| 56 | plugins: [..., nodeResolve({ exportConditions: [..., 'workerd'] })],
|
|---|
| 57 | // don't try to bundle cloudflare:sockets
|
|---|
| 58 | external: [..., 'cloudflare:sockets'],
|
|---|
| 59 | })
|
|---|
| 60 | ```
|
|---|
| 61 | - `esbuild.config.js`
|
|---|
| 62 | ```js
|
|---|
| 63 | await esbuild.build({
|
|---|
| 64 | ...,
|
|---|
| 65 | conditions: [..., 'workerd'],
|
|---|
| 66 | })
|
|---|
| 67 | ```
|
|---|
| 68 |
|
|---|
| 69 | The concrete examples can be found in `packages/pg-bundler-test`.
|
|---|
| 70 |
|
|---|
| 71 | ## How to use conditionally, in non-Node.js environments
|
|---|
| 72 |
|
|---|
| 73 | As implemented in `pg` [here](https://github.com/brianc/node-postgres/commit/07553428e9c0eacf761a5d4541a3300ff7859578#diff-34588ad868ebcb232660aba7ee6a99d1e02f4bc93f73497d2688c3f074e60533R5-R13), a typical use case might look as follows, where in a Node.js environment the `net` module is used, while in a non-Node.js environment, where `net` is unavailable, `pg-cloudflare` is used instead, providing an equivalent interface:
|
|---|
| 74 |
|
|---|
| 75 | ```js
|
|---|
| 76 | module.exports.getStream = function getStream(ssl = false) {
|
|---|
| 77 | const net = require('net')
|
|---|
| 78 | if (typeof net.Socket === 'function') {
|
|---|
| 79 | return net.Socket()
|
|---|
| 80 | }
|
|---|
| 81 | const { CloudflareSocket } = require('pg-cloudflare')
|
|---|
| 82 | return new CloudflareSocket(ssl)
|
|---|
| 83 | }
|
|---|
| 84 | ```
|
|---|
| 85 |
|
|---|
| 86 | ## Node.js implementation of the Socket API proposal
|
|---|
| 87 |
|
|---|
| 88 | If you're looking for a way to rely on `connect()` as the interface you use to interact with raw sockets, but need this interface to be available in a Node.js environment, [`@arrowood.dev/socket`](https://github.com/Ethan-Arrowood/socket) provides a Node.js implementation of the Socket API.
|
|---|
| 89 |
|
|---|
| 90 | ### license
|
|---|
| 91 |
|
|---|
| 92 | The MIT License (MIT)
|
|---|
| 93 |
|
|---|
| 94 | Copyright (c) 2023 Brian M. Carlson
|
|---|
| 95 |
|
|---|
| 96 | Permission is hereby granted, free of charge, to any person obtaining a copy
|
|---|
| 97 | of this software and associated documentation files (the "Software"), to deal
|
|---|
| 98 | in the Software without restriction, including without limitation the rights
|
|---|
| 99 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|---|
| 100 | copies of the Software, and to permit persons to whom the Software is
|
|---|
| 101 | furnished to do so, subject to the following conditions:
|
|---|
| 102 |
|
|---|
| 103 | The above copyright notice and this permission notice shall be included in
|
|---|
| 104 | all copies or substantial portions of the Software.
|
|---|
| 105 |
|
|---|
| 106 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|---|
| 107 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|---|
| 108 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|---|
| 109 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|---|
| 110 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|---|
| 111 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
|---|
| 112 | THE SOFTWARE.
|
|---|