diff --git a/.github/header-checker-lint.yml b/.github/header-checker-lint.yml index 6fe78aa7..19ba2c1b 100644 --- a/.github/header-checker-lint.yml +++ b/.github/header-checker-lint.yml @@ -1,15 +1,21 @@ -{"allowedCopyrightHolders": ["Google LLC"], - "allowedLicenses": ["Apache-2.0", "MIT", "BSD-3"], - "ignoreFiles": ["**/requirements.txt", "**/requirements-test.txt", "**/__init__.py", "samples/**/constraints.txt", "samples/**/constraints-test.txt"], - "sourceFileExtensions": [ - "ts", - "js", - "java", - "sh", - "Dockerfile", - "yaml", - "py", - "html", - "txt" - ] -} \ No newline at end of file +allowedCopyrightHolders: + - "Google LLC" +allowedLicenses: + - "Apache-2.0" +sourceFileExtensions: + - "yaml" + - "yml" + - "sh" + - "proto" + - "Dockerfile" + - "py" + - "html" + - "text" +ignoreFiles: + - ".github/release-please.yml" + - ".github/release-trigger.yml" + - ".github/header-checker-lint.yml" + - ".github/sync-repo-settings.yaml" + - ".kokoro/**" + - "**/requirements.txt" + - "**/requirements*.txt" diff --git a/.github/sync-repo-settings.yaml b/.github/sync-repo-settings.yaml index 7c9ef438..d9236153 100644 --- a/.github/sync-repo-settings.yaml +++ b/.github/sync-repo-settings.yaml @@ -27,7 +27,11 @@ branchProtectionRules: requiredStatusCheckContexts: - "cla/google" - "lint" - - "pg-integration-test-pr (langchain-cloud-sql-testing)" + - "pg-integration-test-pr-py38 (langchain-cloud-sql-testing)" + - "pg-integration-test-pr-py39 (langchain-cloud-sql-testing)" + - "pg-integration-test-pr-py310 (langchain-cloud-sql-testing)" + - "pg-integration-test-pr-py311 (langchain-cloud-sql-testing)" + - "pg-integration-test-pr-py312 (langchain-cloud-sql-testing)" - "conventionalcommits.org" - "header-check" # - Add required status checks like presubmit tests diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml index 9b16c1ca..2352d4b8 100644 --- a/.github/workflows/lint.yml +++ b/.github/workflows/lint.yml @@ -15,12 +15,16 @@ name: Lint on: pull_request: - paths-ignore: + paths-ignore: # Changes to the paths list need to be reflected in lint_fallback.yml - "*.md" + - ".kokoro/**" + - ".github/**" pull_request_target: types: [labeled] paths-ignore: - "*.md" + - ".kokoro/**" + - ".github/**" jobs: lint: @@ -53,6 +57,10 @@ jobs: - name: Checkout Repository uses: actions/checkout@v3 + with: + ref: ${{ github.event.pull_request.head.sha }} + repository: ${{ github.event.pull_request.head.repo.full_name }} + token: ${{ secrets.GITHUB_TOKEN }} - name: Setup Python uses: actions/setup-python@0a5c61591373683505ea898e09a3ea4f39ef2b9c # v5.0.0 diff --git a/.github/workflows/lint_fallback.yml b/.github/workflows/lint_fallback.yml new file mode 100644 index 00000000..04841b9f --- /dev/null +++ b/.github/workflows/lint_fallback.yml @@ -0,0 +1,30 @@ +# Copyright 2024 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. + +name: Lint +on: + pull_request: + paths: # These paths are the inverse of lint.yml + - "*.md" + - ".kokoro/**" + - ".github/**" + +jobs: + lint: + runs-on: ubuntu-latest + permissions: + contents: none + + steps: + - run: echo "No tests required." diff --git a/.kokoro/requirements.txt b/.kokoro/requirements.txt index 844d9807..46415450 100644 --- a/.kokoro/requirements.txt +++ b/.kokoro/requirements.txt @@ -4,25 +4,25 @@ # # pip-compile --generate-hashes requirements.in # -argcomplete==3.1.4 \ - --hash=sha256:72558ba729e4c468572609817226fb0a6e7e9a0a7d477b882be168c0b4a62b94 \ - --hash=sha256:fbe56f8cda08aa9a04b307d8482ea703e96a6a801611acb4be9bf3942017989f +argcomplete==3.2.3 \ + --hash=sha256:bf7900329262e481be5a15f56f19736b376df6f82ed27576fa893652c5de6c23 \ + --hash=sha256:c12355e0494c76a2a7b73e3a59b09024ca0ba1e279fb9ed6c1b82d5b74b6a70c # via nox -attrs==23.1.0 \ - --hash=sha256:1f28b4522cdc2fb4256ac1a020c78acf9cba2c6b461ccd2c126f3aa8e8335d04 \ - --hash=sha256:6279836d581513a26f1bf235f9acd333bc9115683f14f7e8fae46c98fc50e015 +attrs==23.2.0 \ + --hash=sha256:935dc3b529c262f6cf76e50877d35a4bd3c1de194fd41f47a2b7ae8f19971f30 \ + --hash=sha256:99b87a485a5820b23b879f04c2305b44b951b502fd64be915879d77a7e8fc6f1 # via gcp-releasetool -build==1.0.3 \ - --hash=sha256:538aab1b64f9828977f84bc63ae570b060a8ed1be419e7870b8b4fc5e6ea553b \ - --hash=sha256:589bf99a67df7c9cf07ec0ac0e5e2ea5d4b37ac63301c4986d1acb126aa83f8f +build==1.1.1 \ + --hash=sha256:8ed0851ee76e6e38adce47e4bee3b51c771d86c64cf578d0c2245567ee200e73 \ + --hash=sha256:8eea65bb45b1aac2e734ba2cc8dad3a6d97d97901a395bd0ed3e7b46953d2a31 # via -r requirements.in -cachetools==5.3.2 \ - --hash=sha256:086ee420196f7b2ab9ca2db2520aca326318b68fe5ba8bc4d49cca91add450f2 \ - --hash=sha256:861f35a13a451f94e301ce2bec7cac63e881232ccce7ed67fab9b5df4d3beaa1 +cachetools==5.3.3 \ + --hash=sha256:0abad1021d3f8325b2fc1d2e9c8b9c9d57b04c3932657a72465447332c24d945 \ + --hash=sha256:ba29e2dfa0b8b556606f097407ed1aa62080ee108ab0dc5ec9d6a723a007d105 # via google-auth -certifi==2023.7.22 \ - --hash=sha256:539cc1d13202e33ca466e88b2807e29f4c13049d6d87031a3c110744495cb082 \ - --hash=sha256:92d6037539857d8206b8f6ae472e8b77db8058fec5937a1ef3f54304089edbb9 +certifi==2023.11.17 \ + --hash=sha256:9b469f3a900bf28dc19b8cfbf8019bf47f7fdd1a65a1d4ffb98fc14166beb4d1 \ + --hash=sha256:e036ab49d5b79556f99cfc2d9320b34cfbe5be05c5871b51de9329f0603b0474 # via requests cffi==1.16.0 \ --hash=sha256:0c9ef6ff37e974b73c25eecc13952c55bceed9112be2d9d938ded8e856138bcc \ @@ -84,58 +84,58 @@ charset-normalizer==2.1.1 \ # via # -r requirements.in # requests -click==8.0.4 \ - --hash=sha256:6a7a62563bbfabfda3a38f3023a1db4a35978c0abd76f6c9605ecd6554d6d9b1 \ - --hash=sha256:8458d7b1287c5fb128c90e23381cf99dcde74beaf6c7ff6384ce84d6fe090adb +click==8.1.7 \ + --hash=sha256:ae74fb96c20a0277a1d615f1e4d73c8414f5a98db8b799a7931d1582f3390c28 \ + --hash=sha256:ca9853ad459e787e2192211578cc907e7594e294c7ccc834310722b41b9ca6de # via # -r requirements.in # gcp-docuploader # gcp-releasetool -colorlog==6.7.0 \ - --hash=sha256:0d33ca236784a1ba3ff9c532d4964126d8a2c44f1f0cb1d2b0728196f512f662 \ - --hash=sha256:bd94bd21c1e13fac7bd3153f4bc3a7dc0eb0974b8bc2fdf1a989e474f6e582e5 +colorlog==6.8.2 \ + --hash=sha256:3e3e079a41feb5a1b64f978b5ea4f46040a94f11f0e8bbb8261e3dbbeca64d44 \ + --hash=sha256:4dcbb62368e2800cb3c5abd348da7e53f6c362dda502ec27c560b2e58a66bd33 # via # gcp-docuploader # nox -cryptography==42.0.0 \ - --hash=sha256:0a68bfcf57a6887818307600c3c0ebc3f62fbb6ccad2240aa21887cda1f8df1b \ - --hash=sha256:146e971e92a6dd042214b537a726c9750496128453146ab0ee8971a0299dc9bd \ - --hash=sha256:14e4b909373bc5bf1095311fa0f7fcabf2d1a160ca13f1e9e467be1ac4cbdf94 \ - --hash=sha256:206aaf42e031b93f86ad60f9f5d9da1b09164f25488238ac1dc488334eb5e221 \ - --hash=sha256:3005166a39b70c8b94455fdbe78d87a444da31ff70de3331cdec2c568cf25b7e \ - --hash=sha256:324721d93b998cb7367f1e6897370644751e5580ff9b370c0a50dc60a2003513 \ - --hash=sha256:33588310b5c886dfb87dba5f013b8d27df7ffd31dc753775342a1e5ab139e59d \ - --hash=sha256:35cf6ed4c38f054478a9df14f03c1169bb14bd98f0b1705751079b25e1cb58bc \ - --hash=sha256:3ca482ea80626048975360c8e62be3ceb0f11803180b73163acd24bf014133a0 \ - --hash=sha256:56ce0c106d5c3fec1038c3cca3d55ac320a5be1b44bf15116732d0bc716979a2 \ - --hash=sha256:5a217bca51f3b91971400890905a9323ad805838ca3fa1e202a01844f485ee87 \ - --hash=sha256:678cfa0d1e72ef41d48993a7be75a76b0725d29b820ff3cfd606a5b2b33fda01 \ - --hash=sha256:69fd009a325cad6fbfd5b04c711a4da563c6c4854fc4c9544bff3088387c77c0 \ - --hash=sha256:6cf9b76d6e93c62114bd19485e5cb003115c134cf9ce91f8ac924c44f8c8c3f4 \ - --hash=sha256:74f18a4c8ca04134d2052a140322002fef535c99cdbc2a6afc18a8024d5c9d5b \ - --hash=sha256:85f759ed59ffd1d0baad296e72780aa62ff8a71f94dc1ab340386a1207d0ea81 \ - --hash=sha256:87086eae86a700307b544625e3ba11cc600c3c0ef8ab97b0fda0705d6db3d4e3 \ - --hash=sha256:8814722cffcfd1fbd91edd9f3451b88a8f26a5fd41b28c1c9193949d1c689dc4 \ - --hash=sha256:8fedec73d590fd30c4e3f0d0f4bc961aeca8390c72f3eaa1a0874d180e868ddf \ - --hash=sha256:9515ea7f596c8092fdc9902627e51b23a75daa2c7815ed5aa8cf4f07469212ec \ - --hash=sha256:988b738f56c665366b1e4bfd9045c3efae89ee366ca3839cd5af53eaa1401bce \ - --hash=sha256:a2a8d873667e4fd2f34aedab02ba500b824692c6542e017075a2efc38f60a4c0 \ - --hash=sha256:bd7cf7a8d9f34cc67220f1195884151426ce616fdc8285df9054bfa10135925f \ - --hash=sha256:bdce70e562c69bb089523e75ef1d9625b7417c6297a76ac27b1b8b1eb51b7d0f \ - --hash=sha256:be14b31eb3a293fc6e6aa2807c8a3224c71426f7c4e3639ccf1a2f3ffd6df8c3 \ - --hash=sha256:be41b0c7366e5549265adf2145135dca107718fa44b6e418dc7499cfff6b4689 \ - --hash=sha256:c310767268d88803b653fffe6d6f2f17bb9d49ffceb8d70aed50ad45ea49ab08 \ - --hash=sha256:c58115384bdcfe9c7f644c72f10f6f42bed7cf59f7b52fe1bf7ae0a622b3a139 \ - --hash=sha256:c640b0ef54138fde761ec99a6c7dc4ce05e80420262c20fa239e694ca371d434 \ - --hash=sha256:ca20550bb590db16223eb9ccc5852335b48b8f597e2f6f0878bbfd9e7314eb17 \ - --hash=sha256:d97aae66b7de41cdf5b12087b5509e4e9805ed6f562406dfcf60e8481a9a28f8 \ - --hash=sha256:e9326ca78111e4c645f7e49cbce4ed2f3f85e17b61a563328c85a5208cf34440 +cryptography==42.0.5 \ + --hash=sha256:0270572b8bd2c833c3981724b8ee9747b3ec96f699a9665470018594301439ee \ + --hash=sha256:111a0d8553afcf8eb02a4fea6ca4f59d48ddb34497aa8706a6cf536f1a5ec576 \ + --hash=sha256:16a48c23a62a2f4a285699dba2e4ff2d1cff3115b9df052cdd976a18856d8e3d \ + --hash=sha256:1b95b98b0d2af784078fa69f637135e3c317091b615cd0905f8b8a087e86fa30 \ + --hash=sha256:1f71c10d1e88467126f0efd484bd44bca5e14c664ec2ede64c32f20875c0d413 \ + --hash=sha256:2424ff4c4ac7f6b8177b53c17ed5d8fa74ae5955656867f5a8affaca36a27abb \ + --hash=sha256:2bce03af1ce5a5567ab89bd90d11e7bbdff56b8af3acbbec1faded8f44cb06da \ + --hash=sha256:329906dcc7b20ff3cad13c069a78124ed8247adcac44b10bea1130e36caae0b4 \ + --hash=sha256:37dd623507659e08be98eec89323469e8c7b4c1407c85112634ae3dbdb926fdd \ + --hash=sha256:3eaafe47ec0d0ffcc9349e1708be2aaea4c6dd4978d76bf6eb0cb2c13636c6fc \ + --hash=sha256:5e6275c09d2badf57aea3afa80d975444f4be8d3bc58f7f80d2a484c6f9485c8 \ + --hash=sha256:6fe07eec95dfd477eb9530aef5bead34fec819b3aaf6c5bd6d20565da607bfe1 \ + --hash=sha256:7367d7b2eca6513681127ebad53b2582911d1736dc2ffc19f2c3ae49997496bc \ + --hash=sha256:7cde5f38e614f55e28d831754e8a3bacf9ace5d1566235e39d91b35502d6936e \ + --hash=sha256:9481ffe3cf013b71b2428b905c4f7a9a4f76ec03065b05ff499bb5682a8d9ad8 \ + --hash=sha256:98d8dc6d012b82287f2c3d26ce1d2dd130ec200c8679b6213b3c73c08b2b7940 \ + --hash=sha256:a011a644f6d7d03736214d38832e030d8268bcff4a41f728e6030325fea3e400 \ + --hash=sha256:a2913c5375154b6ef2e91c10b5720ea6e21007412f6437504ffea2109b5a33d7 \ + --hash=sha256:a30596bae9403a342c978fb47d9b0ee277699fa53bbafad14706af51fe543d16 \ + --hash=sha256:b03c2ae5d2f0fc05f9a2c0c997e1bc18c8229f392234e8a0194f202169ccd278 \ + --hash=sha256:b6cd2203306b63e41acdf39aa93b86fb566049aeb6dc489b70e34bcd07adca74 \ + --hash=sha256:b7ffe927ee6531c78f81aa17e684e2ff617daeba7f189f911065b2ea2d526dec \ + --hash=sha256:b8cac287fafc4ad485b8a9b67d0ee80c66bf3574f655d3b97ef2e1082360faf1 \ + --hash=sha256:ba334e6e4b1d92442b75ddacc615c5476d4ad55cc29b15d590cc6b86efa487e2 \ + --hash=sha256:ba3e4a42397c25b7ff88cdec6e2a16c2be18720f317506ee25210f6d31925f9c \ + --hash=sha256:c41fb5e6a5fe9ebcd58ca3abfeb51dffb5d83d6775405305bfa8715b76521922 \ + --hash=sha256:cd2030f6650c089aeb304cf093f3244d34745ce0cfcc39f20c6fbfe030102e2a \ + --hash=sha256:cd65d75953847815962c84a4654a84850b2bb4aed3f26fadcc1c13892e1e29f6 \ + --hash=sha256:e4985a790f921508f36f81831817cbc03b102d643b5fcb81cd33df3fa291a1a1 \ + --hash=sha256:e807b3188f9eb0eaa7bbb579b462c5ace579f1cedb28107ce8b48a9f7ad3679e \ + --hash=sha256:f12764b8fffc7a123f641d7d049d382b73f96a34117e0b637b80643169cec8ac \ + --hash=sha256:f8837fe1d6ac4a8052a9a8ddab256bc006242696f03368a4009be7ee3075cdb7 # via # gcp-releasetool # secretstorage -distlib==0.3.7 \ - --hash=sha256:2e24928bc811348f0feb63014e97aaae3037f2cf48712d51ae61df7fd6075057 \ - --hash=sha256:9dafe54b34a028eafd95039d5e5d4851a13734540f1331060d31c9916e7147a8 +distlib==0.3.8 \ + --hash=sha256:034db59a0b96f8ca18035f36290806a9a6e6bd9d1ff91e45a7f172eb17e51784 \ + --hash=sha256:1530ea13e350031b6312d8580ddb6b27a104275a31106523b8f123787f494f64 # via virtualenv docutils==0.20.1 \ --hash=sha256:96f387a2c5562db4476f09f13bbab2192e764cac08ebbf3a34a95d9b1e4a59d6 \ @@ -149,31 +149,31 @@ gcp-docuploader==0.6.5 \ --hash=sha256:30221d4ac3e5a2b9c69aa52fdbef68cc3f27d0e6d0d90e220fc024584b8d2318 \ --hash=sha256:b7458ef93f605b9d46a4bf3a8dc1755dad1f31d030c8679edf304e343b347eea # via -r requirements.in -gcp-releasetool==1.16.0 \ - --hash=sha256:27bf19d2e87aaa884096ff941aa3c592c482be3d6a2bfe6f06afafa6af2353e3 \ - --hash=sha256:a316b197a543fd036209d0caba7a8eb4d236d8e65381c80cbc6d7efaa7606d63 +gcp-releasetool==2.0.0 \ + --hash=sha256:3d73480b50ba243f22d7c7ec08b115a30e1c7817c4899781840c26f9c55b8277 \ + --hash=sha256:7aa9fd935ec61e581eb8458ad00823786d91756c25e492f372b2b30962f3c28f # via -r requirements.in -google-api-core==2.12.0 \ - --hash=sha256:c22e01b1e3c4dcd90998494879612c38d0a3411d1f7b679eb89e2abe3ce1f553 \ - --hash=sha256:ec6054f7d64ad13b41e43d96f735acbd763b0f3b695dabaa2d579673f6a6e160 +google-api-core==2.17.1 \ + --hash=sha256:610c5b90092c360736baccf17bd3efbcb30dd380e7a6dc28a71059edb8bd0d8e \ + --hash=sha256:9df18a1f87ee0df0bc4eea2770ebc4228392d8cc4066655b320e2cfccb15db95 # via # google-cloud-core # google-cloud-storage -google-auth==2.23.4 \ - --hash=sha256:79905d6b1652187def79d491d6e23d0cbb3a21d3c7ba0dbaa9c8a01906b13ff3 \ - --hash=sha256:d4bbc92fe4b8bfd2f3e8d88e5ba7085935da208ee38a134fc280e7ce682a05f2 +google-auth==2.28.2 \ + --hash=sha256:80b8b4969aa9ed5938c7828308f20f035bc79f9d8fb8120bf9dc8db20b41ba30 \ + --hash=sha256:9fd67bbcd40f16d9d42f950228e9cf02a2ded4ae49198b27432d0cded5a74c38 # via # gcp-releasetool # google-api-core # google-cloud-core # google-cloud-storage -google-cloud-core==2.3.3 \ - --hash=sha256:37b80273c8d7eee1ae816b3a20ae43585ea50506cb0e60f3cf5be5f87f1373cb \ - --hash=sha256:fbd11cad3e98a7e5b0343dc07cb1039a5ffd7a5bb96e1f1e27cee4bda4a90863 +google-cloud-core==2.4.1 \ + --hash=sha256:9b7749272a812bde58fff28868d0c5e2f585b82f37e09a1f6ed2d4d10f134073 \ + --hash=sha256:a9e6a4422b9ac5c29f79a0ede9485473338e2ce78d91f2370c01e730eab22e61 # via google-cloud-storage -google-cloud-storage==2.13.0 \ - --hash=sha256:ab0bf2e1780a1b74cf17fccb13788070b729f50c252f0c94ada2aae0ca95437d \ - --hash=sha256:f62dc4c7b6cd4360d072e3deb28035fbdad491ac3d9b0b1815a12daea10f37c7 +google-cloud-storage==2.15.0 \ + --hash=sha256:5d9237f88b648e1d724a0f20b5cde65996a37fe51d75d17660b1404097327dd2 \ + --hash=sha256:7560a3c48a03d66c553dc55215d35883c680fe0ab44c23aa4832800ccc855c74 # via gcp-docuploader google-crc32c==1.5.0 \ --hash=sha256:024894d9d3cfbc5943f8f230e23950cd4906b2fe004c72e29b209420a1e6b05a \ @@ -247,40 +247,42 @@ google-crc32c==1.5.0 \ # via # google-cloud-storage # google-resumable-media -google-resumable-media==2.6.0 \ - --hash=sha256:972852f6c65f933e15a4a210c2b96930763b47197cdf4aa5f5bea435efb626e7 \ - --hash=sha256:fc03d344381970f79eebb632a3c18bb1828593a2dc5572b5f90115ef7d11e81b +google-resumable-media==2.7.0 \ + --hash=sha256:5f18f5fa9836f4b083162064a1c2c98c17239bfda9ca50ad970ccf905f3e625b \ + --hash=sha256:79543cfe433b63fd81c0844b7803aba1bb8950b47bedf7d980c38fa123937e08 # via google-cloud-storage -googleapis-common-protos==1.61.0 \ - --hash=sha256:22f1915393bb3245343f6efe87f6fe868532efc12aa26b391b15132e1279f1c0 \ - --hash=sha256:8a64866a97f6304a7179873a465d6eee97b7a24ec6cfd78e0f575e96b821240b +googleapis-common-protos==1.63.0 \ + --hash=sha256:17ad01b11d5f1d0171c06d3ba5c04c54474e883b66b949722b4938ee2694ef4e \ + --hash=sha256:ae45f75702f7c08b541f750854a678bd8f534a1a6bace6afe975f1d0a82d6632 # via google-api-core -idna==3.4 \ - --hash=sha256:814f528e8dead7d329833b91c5faa87d60bf71824cd12a7530b5526063d02cb4 \ - --hash=sha256:90b77e79eaa3eba6de819a0c442c0b4ceefc341a7a2ab77d7562bf49f425c5c2 +idna==3.6 \ + --hash=sha256:9ecdbbd083b06798ae1e86adcbfe8ab1479cf864e4ee30fe4e46a003d12491ca \ + --hash=sha256:c05567e9c24a6b9faaa835c4821bad0590fbb9d5779e7caa6e1cc4978e7eb24f # via requests -importlib-metadata==6.8.0 \ - --hash=sha256:3ebb78df84a805d7698245025b975d9d67053cd94c79245ba4b3eb694abe68bb \ - --hash=sha256:dbace7892d8c0c4ac1ad096662232f831d4e64f4c4545bd53016a3e9d4654743 +importlib-metadata==6.11.0 \ + --hash=sha256:1231cf92d825c9e03cfc4da076a16de6422c863558229ea0b22b675657463443 \ + --hash=sha256:f0afba6205ad8f8947c7d338b5342d5db2afbfd82f9cbef7879a9539cc12eb9b # via # -r requirements.in # keyring # twine -jaraco-classes==3.3.0 \ +jaraco-classes==3.3.1 \ --hash=sha256:10afa92b6743f25c0cf5f37c6bb6e18e2c5bb84a16527ccfc0040ea377e7aaeb \ --hash=sha256:c063dd08e89217cee02c8d5e5ec560f2c8ce6cdc2fcdc2e68f7b2e5547ed3621 # via keyring jeepney==0.8.0 \ --hash=sha256:5efe48d255973902f6badc3ce55e2aa6c5c3b3bc642059ef3a91247bcfcc5806 \ --hash=sha256:c0a454ad016ca575060802ee4d590dd912e35c122fa04e70306de3d076cce755 - # via secretstorage + # via + # keyring + # secretstorage jinja2==3.1.3 \ --hash=sha256:7d6d50dd97d52cbc355597bd845fabfbac3f551e1f99619e39a35ce8c370b5fa \ --hash=sha256:ac8bd6544d4bb2c9792bf3a159e80bba8fda7f07e81bc3aed565432d5925ba90 # via gcp-releasetool -keyring==24.2.0 \ - --hash=sha256:4901caaf597bfd3bbd78c9a0c7c4c29fcd8310dab2cffefe749e916b6527acd6 \ - --hash=sha256:ca0746a19ec421219f4d713f848fa297a661a8a8c1504867e55bfb5e09091509 +keyring==24.3.1 \ + --hash=sha256:c3327b6ffafc0e8befbdb597cacdb4928ffe5c1212f7645f186e6d9957a898db \ + --hash=sha256:df38a4d7419a6a60fea5cef1e45a948a3e8430dd12ad88b0f423c5c143906218 # via # gcp-releasetool # twine @@ -288,93 +290,93 @@ markdown-it-py==3.0.0 \ --hash=sha256:355216845c60bd96232cd8d8c40e8f9765cc86f46880e43a8fd22dc1a1a8cab1 \ --hash=sha256:e3f60a94fa066dc52ec76661e37c851cb232d92f9886b15cb560aaada2df8feb # via rich -markupsafe==2.1.3 \ - --hash=sha256:05fb21170423db021895e1ea1e1f3ab3adb85d1c2333cbc2310f2a26bc77272e \ - --hash=sha256:0a4e4a1aff6c7ac4cd55792abf96c915634c2b97e3cc1c7129578aa68ebd754e \ - --hash=sha256:10bbfe99883db80bdbaff2dcf681dfc6533a614f700da1287707e8a5d78a8431 \ - --hash=sha256:134da1eca9ec0ae528110ccc9e48041e0828d79f24121a1a146161103c76e686 \ - --hash=sha256:14ff806850827afd6b07a5f32bd917fb7f45b046ba40c57abdb636674a8b559c \ - --hash=sha256:1577735524cdad32f9f694208aa75e422adba74f1baee7551620e43a3141f559 \ - --hash=sha256:1b40069d487e7edb2676d3fbdb2b0829ffa2cd63a2ec26c4938b2d34391b4ecc \ - --hash=sha256:1b8dd8c3fd14349433c79fa8abeb573a55fc0fdd769133baac1f5e07abf54aeb \ - --hash=sha256:1f67c7038d560d92149c060157d623c542173016c4babc0c1913cca0564b9939 \ - --hash=sha256:282c2cb35b5b673bbcadb33a585408104df04f14b2d9b01d4c345a3b92861c2c \ - --hash=sha256:2c1b19b3aaacc6e57b7e25710ff571c24d6c3613a45e905b1fde04d691b98ee0 \ - --hash=sha256:2ef12179d3a291be237280175b542c07a36e7f60718296278d8593d21ca937d4 \ - --hash=sha256:338ae27d6b8745585f87218a3f23f1512dbf52c26c28e322dbe54bcede54ccb9 \ - --hash=sha256:3c0fae6c3be832a0a0473ac912810b2877c8cb9d76ca48de1ed31e1c68386575 \ - --hash=sha256:3fd4abcb888d15a94f32b75d8fd18ee162ca0c064f35b11134be77050296d6ba \ - --hash=sha256:42de32b22b6b804f42c5d98be4f7e5e977ecdd9ee9b660fda1a3edf03b11792d \ - --hash=sha256:47d4f1c5f80fc62fdd7777d0d40a2e9dda0a05883ab11374334f6c4de38adffd \ - --hash=sha256:504b320cd4b7eff6f968eddf81127112db685e81f7e36e75f9f84f0df46041c3 \ - --hash=sha256:525808b8019e36eb524b8c68acdd63a37e75714eac50e988180b169d64480a00 \ - --hash=sha256:56d9f2ecac662ca1611d183feb03a3fa4406469dafe241673d521dd5ae92a155 \ - --hash=sha256:5bbe06f8eeafd38e5d0a4894ffec89378b6c6a625ff57e3028921f8ff59318ac \ - --hash=sha256:65c1a9bcdadc6c28eecee2c119465aebff8f7a584dd719facdd9e825ec61ab52 \ - --hash=sha256:68e78619a61ecf91e76aa3e6e8e33fc4894a2bebe93410754bd28fce0a8a4f9f \ - --hash=sha256:69c0f17e9f5a7afdf2cc9fb2d1ce6aabdb3bafb7f38017c0b77862bcec2bbad8 \ - --hash=sha256:6b2b56950d93e41f33b4223ead100ea0fe11f8e6ee5f641eb753ce4b77a7042b \ - --hash=sha256:715d3562f79d540f251b99ebd6d8baa547118974341db04f5ad06d5ea3eb8007 \ - --hash=sha256:787003c0ddb00500e49a10f2844fac87aa6ce977b90b0feaaf9de23c22508b24 \ - --hash=sha256:7ef3cb2ebbf91e330e3bb937efada0edd9003683db6b57bb108c4001f37a02ea \ - --hash=sha256:8023faf4e01efadfa183e863fefde0046de576c6f14659e8782065bcece22198 \ - --hash=sha256:8758846a7e80910096950b67071243da3e5a20ed2546e6392603c096778d48e0 \ - --hash=sha256:8afafd99945ead6e075b973fefa56379c5b5c53fd8937dad92c662da5d8fd5ee \ - --hash=sha256:8c41976a29d078bb235fea9b2ecd3da465df42a562910f9022f1a03107bd02be \ - --hash=sha256:8e254ae696c88d98da6555f5ace2279cf7cd5b3f52be2b5cf97feafe883b58d2 \ - --hash=sha256:8f9293864fe09b8149f0cc42ce56e3f0e54de883a9de90cd427f191c346eb2e1 \ - --hash=sha256:9402b03f1a1b4dc4c19845e5c749e3ab82d5078d16a2a4c2cd2df62d57bb0707 \ - --hash=sha256:962f82a3086483f5e5f64dbad880d31038b698494799b097bc59c2edf392fce6 \ - --hash=sha256:9aad3c1755095ce347e26488214ef77e0485a3c34a50c5a5e2471dff60b9dd9c \ - --hash=sha256:9dcdfd0eaf283af041973bff14a2e143b8bd64e069f4c383416ecd79a81aab58 \ - --hash=sha256:aa57bd9cf8ae831a362185ee444e15a93ecb2e344c8e52e4d721ea3ab6ef1823 \ - --hash=sha256:aa7bd130efab1c280bed0f45501b7c8795f9fdbeb02e965371bbef3523627779 \ - --hash=sha256:ab4a0df41e7c16a1392727727e7998a467472d0ad65f3ad5e6e765015df08636 \ - --hash=sha256:ad9e82fb8f09ade1c3e1b996a6337afac2b8b9e365f926f5a61aacc71adc5b3c \ - --hash=sha256:af598ed32d6ae86f1b747b82783958b1a4ab8f617b06fe68795c7f026abbdcad \ - --hash=sha256:b076b6226fb84157e3f7c971a47ff3a679d837cf338547532ab866c57930dbee \ - --hash=sha256:b7ff0f54cb4ff66dd38bebd335a38e2c22c41a8ee45aa608efc890ac3e3931bc \ - --hash=sha256:bfce63a9e7834b12b87c64d6b155fdd9b3b96191b6bd334bf37db7ff1fe457f2 \ - --hash=sha256:c011a4149cfbcf9f03994ec2edffcb8b1dc2d2aede7ca243746df97a5d41ce48 \ - --hash=sha256:c9c804664ebe8f83a211cace637506669e7890fec1b4195b505c214e50dd4eb7 \ - --hash=sha256:ca379055a47383d02a5400cb0d110cef0a776fc644cda797db0c5696cfd7e18e \ - --hash=sha256:cb0932dc158471523c9637e807d9bfb93e06a95cbf010f1a38b98623b929ef2b \ - --hash=sha256:cd0f502fe016460680cd20aaa5a76d241d6f35a1c3350c474bac1273803893fa \ - --hash=sha256:ceb01949af7121f9fc39f7d27f91be8546f3fb112c608bc4029aef0bab86a2a5 \ - --hash=sha256:d080e0a5eb2529460b30190fcfcc4199bd7f827663f858a226a81bc27beaa97e \ - --hash=sha256:dd15ff04ffd7e05ffcb7fe79f1b98041b8ea30ae9234aed2a9168b5797c3effb \ - --hash=sha256:df0be2b576a7abbf737b1575f048c23fb1d769f267ec4358296f31c2479db8f9 \ - --hash=sha256:e09031c87a1e51556fdcb46e5bd4f59dfb743061cf93c4d6831bf894f125eb57 \ - --hash=sha256:e4dd52d80b8c83fdce44e12478ad2e85c64ea965e75d66dbeafb0a3e77308fcc \ - --hash=sha256:f698de3fd0c4e6972b92290a45bd9b1536bffe8c6759c62471efaa8acb4c37bc \ - --hash=sha256:fec21693218efe39aa7f8599346e90c705afa52c5b31ae019b2e57e8f6542bb2 \ - --hash=sha256:ffcc3f7c66b5f5b7931a5aa68fc9cecc51e685ef90282f4a82f0f5e9b704ad11 +MarkupSafe==2.1.5 \ + --hash=sha256:00e046b6dd71aa03a41079792f8473dc494d564611a8f89bbbd7cb93295ebdcf \ + --hash=sha256:075202fa5b72c86ad32dc7d0b56024ebdbcf2048c0ba09f1cde31bfdd57bcfff \ + --hash=sha256:0e397ac966fdf721b2c528cf028494e86172b4feba51d65f81ffd65c63798f3f \ + --hash=sha256:17b950fccb810b3293638215058e432159d2b71005c74371d784862b7e4683f3 \ + --hash=sha256:1f3fbcb7ef1f16e48246f704ab79d79da8a46891e2da03f8783a5b6fa41a9532 \ + --hash=sha256:2174c595a0d73a3080ca3257b40096db99799265e1c27cc5a610743acd86d62f \ + --hash=sha256:2b7c57a4dfc4f16f7142221afe5ba4e093e09e728ca65c51f5620c9aaeb9a617 \ + --hash=sha256:2d2d793e36e230fd32babe143b04cec8a8b3eb8a3122d2aceb4a371e6b09b8df \ + --hash=sha256:30b600cf0a7ac9234b2638fbc0fb6158ba5bdcdf46aeb631ead21248b9affbc4 \ + --hash=sha256:397081c1a0bfb5124355710fe79478cdbeb39626492b15d399526ae53422b906 \ + --hash=sha256:3a57fdd7ce31c7ff06cdfbf31dafa96cc533c21e443d57f5b1ecc6cdc668ec7f \ + --hash=sha256:3c6b973f22eb18a789b1460b4b91bf04ae3f0c4234a0a6aa6b0a92f6f7b951d4 \ + --hash=sha256:3e53af139f8579a6d5f7b76549125f0d94d7e630761a2111bc431fd820e163b8 \ + --hash=sha256:4096e9de5c6fdf43fb4f04c26fb114f61ef0bf2e5604b6ee3019d51b69e8c371 \ + --hash=sha256:4275d846e41ecefa46e2015117a9f491e57a71ddd59bbead77e904dc02b1bed2 \ + --hash=sha256:4c31f53cdae6ecfa91a77820e8b151dba54ab528ba65dfd235c80b086d68a465 \ + --hash=sha256:4f11aa001c540f62c6166c7726f71f7573b52c68c31f014c25cc7901deea0b52 \ + --hash=sha256:5049256f536511ee3f7e1b3f87d1d1209d327e818e6ae1365e8653d7e3abb6a6 \ + --hash=sha256:58c98fee265677f63a4385256a6d7683ab1832f3ddd1e66fe948d5880c21a169 \ + --hash=sha256:598e3276b64aff0e7b3451b72e94fa3c238d452e7ddcd893c3ab324717456bad \ + --hash=sha256:5b7b716f97b52c5a14bffdf688f971b2d5ef4029127f1ad7a513973cfd818df2 \ + --hash=sha256:5dedb4db619ba5a2787a94d877bc8ffc0566f92a01c0ef214865e54ecc9ee5e0 \ + --hash=sha256:619bc166c4f2de5caa5a633b8b7326fbe98e0ccbfacabd87268a2b15ff73a029 \ + --hash=sha256:629ddd2ca402ae6dbedfceeba9c46d5f7b2a61d9749597d4307f943ef198fc1f \ + --hash=sha256:656f7526c69fac7f600bd1f400991cc282b417d17539a1b228617081106feb4a \ + --hash=sha256:6ec585f69cec0aa07d945b20805be741395e28ac1627333b1c5b0105962ffced \ + --hash=sha256:72b6be590cc35924b02c78ef34b467da4ba07e4e0f0454a2c5907f473fc50ce5 \ + --hash=sha256:7502934a33b54030eaf1194c21c692a534196063db72176b0c4028e140f8f32c \ + --hash=sha256:7a68b554d356a91cce1236aa7682dc01df0edba8d043fd1ce607c49dd3c1edcf \ + --hash=sha256:7b2e5a267c855eea6b4283940daa6e88a285f5f2a67f2220203786dfa59b37e9 \ + --hash=sha256:823b65d8706e32ad2df51ed89496147a42a2a6e01c13cfb6ffb8b1e92bc910bb \ + --hash=sha256:8590b4ae07a35970728874632fed7bd57b26b0102df2d2b233b6d9d82f6c62ad \ + --hash=sha256:8dd717634f5a044f860435c1d8c16a270ddf0ef8588d4887037c5028b859b0c3 \ + --hash=sha256:8dec4936e9c3100156f8a2dc89c4b88d5c435175ff03413b443469c7c8c5f4d1 \ + --hash=sha256:97cafb1f3cbcd3fd2b6fbfb99ae11cdb14deea0736fc2b0952ee177f2b813a46 \ + --hash=sha256:a17a92de5231666cfbe003f0e4b9b3a7ae3afb1ec2845aadc2bacc93ff85febc \ + --hash=sha256:a549b9c31bec33820e885335b451286e2969a2d9e24879f83fe904a5ce59d70a \ + --hash=sha256:ac07bad82163452a6884fe8fa0963fb98c2346ba78d779ec06bd7a6262132aee \ + --hash=sha256:ae2ad8ae6ebee9d2d94b17fb62763125f3f374c25618198f40cbb8b525411900 \ + --hash=sha256:b91c037585eba9095565a3556f611e3cbfaa42ca1e865f7b8015fe5c7336d5a5 \ + --hash=sha256:bc1667f8b83f48511b94671e0e441401371dfd0f0a795c7daa4a3cd1dde55bea \ + --hash=sha256:bec0a414d016ac1a18862a519e54b2fd0fc8bbfd6890376898a6c0891dd82e9f \ + --hash=sha256:bf50cd79a75d181c9181df03572cdce0fbb75cc353bc350712073108cba98de5 \ + --hash=sha256:bff1b4290a66b490a2f4719358c0cdcd9bafb6b8f061e45c7a2460866bf50c2e \ + --hash=sha256:c061bb86a71b42465156a3ee7bd58c8c2ceacdbeb95d05a99893e08b8467359a \ + --hash=sha256:c8b29db45f8fe46ad280a7294f5c3ec36dbac9491f2d1c17345be8e69cc5928f \ + --hash=sha256:ce409136744f6521e39fd8e2a24c53fa18ad67aa5bc7c2cf83645cce5b5c4e50 \ + --hash=sha256:d050b3361367a06d752db6ead6e7edeb0009be66bc3bae0ee9d97fb326badc2a \ + --hash=sha256:d283d37a890ba4c1ae73ffadf8046435c76e7bc2247bbb63c00bd1a709c6544b \ + --hash=sha256:d9fad5155d72433c921b782e58892377c44bd6252b5af2f67f16b194987338a4 \ + --hash=sha256:daa4ee5a243f0f20d528d939d06670a298dd39b1ad5f8a72a4275124a7819eff \ + --hash=sha256:db0b55e0f3cc0be60c1f19efdde9a637c32740486004f20d1cff53c3c0ece4d2 \ + --hash=sha256:e61659ba32cf2cf1481e575d0462554625196a1f2fc06a1c777d3f48e8865d46 \ + --hash=sha256:ea3d8a3d18833cf4304cd2fc9cbb1efe188ca9b5efef2bdac7adc20594a0e46b \ + --hash=sha256:ec6a563cff360b50eed26f13adc43e61bc0c04d94b8be985e6fb24b81f6dcfdf \ + --hash=sha256:f5dfb42c4604dddc8e4305050aa6deb084540643ed5804d7455b5df8fe16f5e5 \ + --hash=sha256:fa173ec60341d6bb97a89f5ea19c85c5643c1e7dedebc22f5181eb73573142c5 \ + --hash=sha256:fa9db3f79de01457b03d4f01b34cf91bc0048eb2c3846ff26f66687c2f6d16ab \ + --hash=sha256:fce659a462a1be54d2ffcacea5e3ba2d74daa74f30f5f143fe0c58636e355fdd \ + --hash=sha256:ffee1f21e5ef0d712f9033568f8344d5da8cc2869dbd08d87c84656e6a2d2f68 # via jinja2 mdurl==0.1.2 \ --hash=sha256:84008a41e51615a49fc9966191ff91509e3c40b939176e643fd50a5c2196b8f8 \ --hash=sha256:bb413d29f5eea38f31dd4754dd7377d4465116fb207585f97bf925588687c1ba # via markdown-it-py -more-itertools==10.1.0 \ - --hash=sha256:626c369fa0eb37bac0291bce8259b332fd59ac792fa5497b59837309cd5b114a \ - --hash=sha256:64e0735fcfdc6f3464ea133afe8ea4483b1c5fe3a3d69852e6503b43a0b222e6 +more-itertools==10.2.0 \ + --hash=sha256:686b06abe565edfab151cb8fd385a05651e1fdf8f0a14191e4439283421f8684 \ + --hash=sha256:8fccb480c43d3e99a00087634c06dd02b0d50fbf088b380de5a41a015ec239e1 # via jaraco-classes -nh3==0.2.14 \ - --hash=sha256:116c9515937f94f0057ef50ebcbcc10600860065953ba56f14473ff706371873 \ - --hash=sha256:18415df36db9b001f71a42a3a5395db79cf23d556996090d293764436e98e8ad \ - --hash=sha256:203cac86e313cf6486704d0ec620a992c8bc164c86d3a4fd3d761dd552d839b5 \ - --hash=sha256:2b0be5c792bd43d0abef8ca39dd8acb3c0611052ce466d0401d51ea0d9aa7525 \ - --hash=sha256:377aaf6a9e7c63962f367158d808c6a1344e2b4f83d071c43fbd631b75c4f0b2 \ - --hash=sha256:525846c56c2bcd376f5eaee76063ebf33cf1e620c1498b2a40107f60cfc6054e \ - --hash=sha256:5529a3bf99402c34056576d80ae5547123f1078da76aa99e8ed79e44fa67282d \ - --hash=sha256:7771d43222b639a4cd9e341f870cee336b9d886de1ad9bec8dddab22fe1de450 \ - --hash=sha256:88c753efbcdfc2644a5012938c6b9753f1c64a5723a67f0301ca43e7b85dcf0e \ - --hash=sha256:93a943cfd3e33bd03f77b97baa11990148687877b74193bf777956b67054dcc6 \ - --hash=sha256:9be2f68fb9a40d8440cbf34cbf40758aa7f6093160bfc7fb018cce8e424f0c3a \ - --hash=sha256:a0c509894fd4dccdff557068e5074999ae3b75f4c5a2d6fb5415e782e25679c4 \ - --hash=sha256:ac8056e937f264995a82bf0053ca898a1cb1c9efc7cd68fa07fe0060734df7e4 \ - --hash=sha256:aed56a86daa43966dd790ba86d4b810b219f75b4bb737461b6886ce2bde38fd6 \ - --hash=sha256:e8986f1dd3221d1e741fda0a12eaa4a273f1d80a35e31a1ffe579e7c621d069e \ - --hash=sha256:f99212a81c62b5f22f9e7c3e347aa00491114a5647e1f13bbebd79c3e5f08d75 +nh3==0.2.15 \ + --hash=sha256:0d02d0ff79dfd8208ed25a39c12cbda092388fff7f1662466e27d97ad011b770 \ + --hash=sha256:3277481293b868b2715907310c7be0f1b9d10491d5adf9fce11756a97e97eddf \ + --hash=sha256:3b803a5875e7234907f7d64777dfde2b93db992376f3d6d7af7f3bc347deb305 \ + --hash=sha256:427fecbb1031db085eaac9931362adf4a796428ef0163070c484b5a768e71601 \ + --hash=sha256:5f0d77272ce6d34db6c87b4f894f037d55183d9518f948bba236fe81e2bb4e28 \ + --hash=sha256:60684857cfa8fdbb74daa867e5cad3f0c9789415aba660614fe16cd66cbb9ec7 \ + --hash=sha256:6f42f99f0cf6312e470b6c09e04da31f9abaadcd3eb591d7d1a88ea931dca7f3 \ + --hash=sha256:86e447a63ca0b16318deb62498db4f76fc60699ce0a1231262880b38b6cff911 \ + --hash=sha256:8d595df02413aa38586c24811237e95937ef18304e108b7e92c890a06793e3bf \ + --hash=sha256:9c0d415f6b7f2338f93035bba5c0d8c1b464e538bfbb1d598acd47d7969284f0 \ + --hash=sha256:a5167a6403d19c515217b6bcaaa9be420974a6ac30e0da9e84d4fc67a5d474c5 \ + --hash=sha256:ac19c0d68cd42ecd7ead91a3a032fdfff23d29302dbb1311e641a130dfefba97 \ + --hash=sha256:b1e97221cedaf15a54f5243f2c5894bb12ca951ae4ddfd02a9d4ea9df9e1a29d \ + --hash=sha256:bc2d086fb540d0fa52ce35afaded4ea526b8fc4d3339f783db55c95de40ef02e \ + --hash=sha256:d1e30ff2d8d58fb2a14961f7aac1bbb1c51f9bdd7da727be35c63826060b0bf3 \ + --hash=sha256:f3b53ba93bb7725acab1e030bc2ecd012a817040fd7851b332f86e2f9bb98dc6 # via readme-renderer nox==2023.4.22 \ --hash=sha256:0b1adc619c58ab4fa57d6ab2e7823fe47a32e70202f287d78474adcc7bda1891 \ @@ -387,9 +389,9 @@ packaging==23.2 \ # build # gcp-releasetool # nox -pkginfo==1.9.6 \ - --hash=sha256:4b7a555a6d5a22169fcc9cf7bfd78d296b0361adad412a346c1226849af5e546 \ - --hash=sha256:8fd5896e8718a4372f0ea9cc9d96f6417c9b986e23a4d116dda26b62cc29d046 +pkginfo==1.10.0 \ + --hash=sha256:5df73835398d10db79f8eecd5cd86b1f6d29317589ea70796994d49399af6297 \ + --hash=sha256:889a6da2ed7ffc58ab5b900d888ddce90bce912f2d2de1dc1c26f4cb9fe65097 # via twine platformdirs==3.11.0 \ --hash=sha256:cf8ee52a3afdb965072dcc652433e0c7e3e40cf5ea1477cd4b3b1d2eb75495b3 \ @@ -423,9 +425,9 @@ protobuf==3.20.3 \ # gcp-releasetool # google-api-core # googleapis-common-protos -pyasn1==0.5.0 \ - --hash=sha256:87a2121042a1ac9358cabcaf1d07680ff97ee6404333bacca15f76aa8ad01a57 \ - --hash=sha256:97b7290ca68e62a832558ec3976f15cbf911bf5d7c7039d8b861c2a0ece69fde +pyasn1==0.5.1 \ + --hash=sha256:4439847c58d40b1d0a573d07e3856e95333f1976294494c325775aeca506eb58 \ + --hash=sha256:6d391a96e59b23130a5cfa74d6fd7f388dbbe26cc8f1edf39fdddf08d9d6676c # via # pyasn1-modules # rsa @@ -437,9 +439,9 @@ pycparser==2.21 \ --hash=sha256:8ee45429555515e1f6b185e78100aea234072576aa43ab53aefcae078162fca9 \ --hash=sha256:e644fdec12f7872f86c58ff790da456218b10f863970249516d60a5eaca77206 # via cffi -pygments==2.16.1 \ - --hash=sha256:13fc09fa63bc8d8671a6d247e1eb303c4b343eaee81d861f3404db2935653692 \ - --hash=sha256:1daff0494820c69bc8941e407aa20f577374ee88364ee10a98fdbe0aece96e29 +Pygments==2.17.2 \ + --hash=sha256:b27c2826c47d0f3219f29554824c30c5e8945175d888647acd804ddd04af846c \ + --hash=sha256:da46cec9fd2de5be3a8a784f434e4c4ab670b4ff54d605c4c2717e9d49c4c367 # via # readme-renderer # rich @@ -454,9 +456,9 @@ pyproject-hooks==1.0.0 \ --hash=sha256:283c11acd6b928d2f6a7c73fa0d01cb2bdc5f07c57a2eeb6e83d5e56b97976f8 \ --hash=sha256:f271b298b97f5955d53fb12b72c1fb1948c22c1a6b70b315c54cedaca0264ef5 # via build -python-dateutil==2.8.2 \ - --hash=sha256:0123cacc1627ae19ddf3c27a5de5bd67ee4586fbdd6440d9748f8abb483d3e86 \ - --hash=sha256:961d03dc3453ebbc59dbdea9e4e11c5651520a876d0f4db161e8674aae935da9 +python-dateutil==2.9.0.post0 \ + --hash=sha256:37dd54208da7e1cd875388217d5e00ebd4179249f90fb72437e91a35459a0ad3 \ + --hash=sha256:a8b2bc7bffae282281c8140a97d3aa9c14da0b136dfe83f850eea9a5f7470427 # via gcp-releasetool readme-renderer==42.0 \ --hash=sha256:13d039515c1f24de668e2c93f2e877b9dbe6c6c32328b90a40a49d8b2b85f36d \ @@ -479,9 +481,9 @@ rfc3986==2.0.0 \ --hash=sha256:50b1502b60e289cb37883f3dfd34532b8873c7de9f49bb546641ce9cbd256ebd \ --hash=sha256:97aacf9dbd4bfd829baad6e6309fa6573aaf1be3f6fa735c8ab05e46cecb261c # via twine -rich==13.6.0 \ - --hash=sha256:2b38e2fe9ca72c9a00170a1a2d20c63c790d0e10ef1fe35eba76e1e7b1d7d245 \ - --hash=sha256:5c14d22737e6d5084ef4771b62d5d4363165b403455a30a1c8ca39dc7b644bef +rich==13.7.1 \ + --hash=sha256:4edbae314f59eb482f54e9e30bf00d33350aaa94f4bfcd4e9e3110e64d0d7222 \ + --hash=sha256:9be308cb1fe2f1f57d67ce99e95af38a1e2bc71ad9813b0e247cf7ffbcc3a432 # via twine rsa==4.9 \ --hash=sha256:90260d9058e514786967344d0ef75fa8727eed8a7d2e43ce9f4bcf1b536174f7 \ @@ -490,7 +492,9 @@ rsa==4.9 \ secretstorage==3.3.3 \ --hash=sha256:2403533ef369eca6d2ba81718576c5e0f564d5cca1b58f73a8b23e7d4eeebd77 \ --hash=sha256:f356e6628222568e3af06f2eba8df495efa13b3b63081dafd4f7d9a7b7bc9f99 - # via -r requirements.in + # via + # -r requirements.in + # keyring six==1.16.0 \ --hash=sha256:1e61c37477a1626458e36f7b1d82aa5c9b094fa4802892072e49de9c60c4c926 \ --hash=sha256:8abb2f1d86890a2dfb989f9a77cfcfd3e47c2a354b01111771326f8aa26e0254 @@ -505,30 +509,33 @@ twine==4.0.2 \ --hash=sha256:929bc3c280033347a00f847236564d1c52a3e61b1ac2516c97c48f3ceab756d8 \ --hash=sha256:9e102ef5fdd5a20661eb88fad46338806c3bd32cf1db729603fe3697b1bc83c8 # via -r requirements.in -typing-extensions==4.8.0 \ - --hash=sha256:8f92fc8806f9a6b641eaa5318da32b44d401efaac0f6678c9bc448ba3605faa0 \ - --hash=sha256:df8e4339e9cb77357558cbdbceca33c303714cf861d1eef15e1070055ae8b7ef +typing-extensions==4.10.0 \ + --hash=sha256:69b1a937c3a517342112fb4c6df7e72fc39a38e7891a5730ed4985b5214b5475 \ + --hash=sha256:b0abd7c89e8fb96f98db18d86106ff1d90ab692004eb746cf6eda2682f91b3cb # via -r requirements.in -urllib3==2.0.7 \ - --hash=sha256:c97dfde1f7bd43a71c8d2a58e369e9b2bf692d1334ea9f9cae55add7d0dd0f84 \ - --hash=sha256:fdb6d215c776278489906c2f8916e6e7d4f5a9b602ccbcfdf7f016fc8da0596e +urllib3==2.2.1 \ + --hash=sha256:450b20ec296a467077128bff42b73080516e71b56ff59a60a02bef2232c4fa9d \ + --hash=sha256:d0570876c61ab9e520d776c38acbbb5b05a776d3f9ff98a5c8fd5162a444cf19 # via # requests # twine -virtualenv==20.24.6 \ - --hash=sha256:02ece4f56fbf939dbbc33c0715159951d6bf14aaf5457b092e4548e1382455af \ - --hash=sha256:520d056652454c5098a00c0f073611ccbea4c79089331f60bf9d7ba247bb7381 +virtualenv==20.25.1 \ + --hash=sha256:961c026ac520bac5f69acb8ea063e8a4f071bcc9457b9c1f28f6b085c511583a \ + --hash=sha256:e08e13ecdca7a0bd53798f356d5831434afa5b07b93f0abdf0797b7a06ffe197 # via nox -wheel==0.41.3 \ - --hash=sha256:488609bc63a29322326e05560731bf7bfea8e48ad646e1f5e40d366607de0942 \ - --hash=sha256:4d4987ce51a49370ea65c0bfd2234e8ce80a12780820d9dc462597a6e60d0841 +wheel==0.43.0 \ + --hash=sha256:465ef92c69fa5c5da2d1cf8ac40559a8c940886afcef87dcf14b9470862f1d85 \ + --hash=sha256:55c570405f142630c6b9f72fe09d9b67cf1477fcf543ae5b8dcb1f5b7377da81 # via -r requirements.in -zipp==3.17.0 \ - --hash=sha256:0e923e726174922dce09c53c59ad483ff7bbb8e572e00c7f7c46b88556409f31 \ - --hash=sha256:84e64a1c28cf7e91ed2078bb8cc8c259cb19b76942096c8d7b84947690cabaf0 +zipp==3.18.1 \ + --hash=sha256:206f5a15f2af3dbaee80769fb7dc6f249695e940acca08dfb2a4769fe61e538b \ + --hash=sha256:2884ed22e7d8961de1c9a05142eb69a247f120291bc0206a00a7642f09b5b715 # via importlib-metadata # WARNING: The following packages were not pinned, but pip requires them to be # pinned when the requirements file includes hashes and the requirement is not # satisfied by a package already installed. Consider using the --allow-unsafe flag. # setuptools +jaraco.classes==3.3.1 \ + --hash=sha256:86b534de565381f6b3c1c830d13f931d7be1a75f0081c57dff615578676e2206 \ + --hash=sha256:cb28a5ebda8bc47d8c8015307d93163464f9f2b91ab4006e09ff0ce07e8bfb30 diff --git a/CHANGELOG.md b/CHANGELOG.md index b1a5bfbf..171cd22e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,25 @@ # Changelog +## [0.2.0](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/compare/v0.1.0...v0.2.0) (2024-03-25) + + +### Features + +* **ci:** Test against multiple versions ([#86](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/issues/86)) ([a3f410d](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/commit/a3f410d1bfda87aa3904d153140937c8e2a415f2)) + + +### Bug Fixes + +* Sql statement for non-nullable column ([#85](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/issues/85)) ([e143e14](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/commit/e143e14cc8ea12399be81c49f579a6c9872119ea)) + + +### Documentation + +* Add check for database ([#79](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/issues/79)) ([4959ceb](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/commit/4959ceb78aae27c8b5d48168ec096b8cd01b6e82)) +* Add github links ([#84](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/issues/84)) ([864f642](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/commit/864f642c19b3409acffaea7c6479791b12dd059c)) +* Update langchain_quick_start.ipynb ([#81](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/issues/81)) ([5e79043](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/commit/5e790436073b8c6e37be905a6215dc9ea5602adc)) +* Update quickstart ([#76](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/issues/76)) ([37b4380](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/commit/37b4380871f50dc30274539d0f8a65664d023d35)) + ## 0.1.0 (2024-02-28) diff --git a/DEVELOPER.md b/DEVELOPER.md new file mode 100644 index 00000000..70571d78 --- /dev/null +++ b/DEVELOPER.md @@ -0,0 +1,82 @@ +# DEVELOPER.md + +## Versioning + +This library follows [Semantic Versioning](http://semver.org/). + +## Processes + +### Conventional Commit messages + +This repository uses tool [Release Please](https://github.com/googleapis/release-please) to create GitHub and PyPi releases. It does so by parsing your +git history, looking for [Conventional Commit messages](https://www.conventionalcommits.org/), +and creating release PRs. + +Learn more by reading [How should I write my commits?](https://github.com/googleapis/release-please?tab=readme-ov-file#how-should-i-write-my-commits) + +## Testing + +### Run tests locally + +1. Set environment variables for `INSTANCE_ID`, `DATABASE_ID`, `REGION`, `DB_USER`, `DB_PASSWORD` + +1. Run pytest to automatically run all tests: + + ```bash + pytest + ``` + +### CI Platform Setup + +Cloud Build is used to run tests against Google Cloud resources in test project: langchain-alloydb-testing. +Each test has a corresponding Cloud Build trigger, see [all triggers][triggers]. +These tests are registered as required tests in `.github/sync-repo-settings.yaml`. + +#### Trigger Setup + +Cloud Build triggers (for Python versions 3.8 to 3.11) were created with the following specs: + +```YAML +name: pg-integration-test-pr-py38 +description: Run integration tests on PR for Python 3.8 +filename: integration.cloudbuild.yaml +github: + name: langchain-google-alloydb-pg-python + owner: googleapis + pullRequest: + branch: .* + commentControl: COMMENTS_ENABLED_FOR_EXTERNAL_CONTRIBUTORS_ONLY +ignoredFiles: + - docs/** + - .kokoro/** + - .github/** + - "*.md" +substitutions: + _CLUSTER_ID: + _DATABASE_ID: + _INSTANCE_ID: + _REGION: us-central1 + _VERSION: "3.8" +``` + +Use `gcloud builds triggers import --source=trigger.yaml` create triggers via the command line + +#### Project Setup + +1. Create an Cloud SQL for PostgreSQL instance and database +1. Setup Cloud Build triggers (above) + +#### Run tests with Cloud Build + +* Run integration test: + + ```bash + gcloud builds submit --config integration.cloudbuild.yaml --region us-central1 --substitutions=_INSTANCE_ID=$INSTANCE_ID,_DATABASE_ID=$DATABASE_ID,_REGION=$REGION + ``` + +#### Trigger + +To run Cloud Build tests on GitHub from external contributors, ie RenovateBot, comment: `/gcbrun`. + + +[triggers]: https://console.cloud.google.com/cloud-build/triggers?e=13802955&project=langchain-cloud-sql-testing \ No newline at end of file diff --git a/README.md b/README.md index 26b805fe..fd33d455 100644 --- a/README.md +++ b/README.md @@ -42,7 +42,7 @@ from langchain_google_cloud_sql_pg import PostgresVectorstore, PostgresEngine from langchain.embeddings import VertexAIEmbeddings -engine = PostgresEngine.from_instance("region", "my-instance", "my-database") +engine = PostgresEngine.from_instance("project-id", "region", "my-instance", "my-database") embeddings_service = VertexAIEmbeddings() vectorstore = PostgresVectorStore( engine, @@ -61,7 +61,7 @@ Use a document loader to load data as LangChain `Document`s. from langchain_google_cloud_sql_pg import PostgresEngine, PostgresLoader -engine = PostgresEngine.from_instance("region", "my-instance", "my-database") +engine = PostgresEngine.from_instance("project-id", "region", "my-instance", "my-database") loader = PostgresSQLLoader( engine, table_name="my-table-name" @@ -79,7 +79,7 @@ Use `ChatMessageHistory` to store messages and provide conversation history to L from langchain_google_cloud_sql_pg import PostgresChatMessageHistory, PostgresEngine -engine = PostgresEngine.from_instance("region", "my-instance", "my-database") +engine = PostgresEngine.from_instance("project-id", "region", "my-instance", "my-database") history = PostgresChatMessageHistory( engine, table_name="my-message-store", diff --git a/docs/chat_message_history.ipynb b/docs/chat_message_history.ipynb index be727c6a..c24d2660 100644 --- a/docs/chat_message_history.ipynb +++ b/docs/chat_message_history.ipynb @@ -1,552 +1,558 @@ { - "cells": [ - { - "cell_type": "markdown", - "id": "f22eab3f84cbeb37", - "metadata": { - "id": "f22eab3f84cbeb37" - }, - "source": [ - "# Google Cloud SQL for PostgreSQL\n", - "\n", - "> [Cloud SQL](https://cloud.google.com/sql) is a fully managed relational database service that offers high performance, seamless integration, and impressive scalability. It offers MySQL, PostgreSQL, and SQL Server database engines. Extend your database application to build AI-powered experiences leveraging Cloud SQL's Langchain integrations.\n", - "\n", - "This notebook goes over how to use `Cloud SQL for PostgreSQL` to store chat message history with the `PostgresChatMessageHistory` class." - ] - }, - { - "cell_type": "markdown", - "id": "da400c79-a360-43e2-be60-401fd02b2819", - "metadata": { - "id": "da400c79-a360-43e2-be60-401fd02b2819" - }, - "source": [ - "## Before You Begin\n", - "\n", - "To run this notebook, you will need to do the following:\n", - " * [Create a Google Cloud Project](https://developers.google.com/workspace/guides/create-project)\n", - " * [Create a Cloud SQL for PostgreSQL instance](https://cloud.google.com/sql/docs/postgres/create-instance)\n", - " * [Create a Cloud SQL database](https://cloud.google.com/sql/docs/mysql/create-manage-databases)\n", - " * [Add an IAM database user to the database](https://cloud.google.com/sql/docs/postgres/add-manage-iam-users#creating-a-database-user) (Optional)" - ] - }, - { - "cell_type": "markdown", - "id": "Mm7-fG_LltD7", - "metadata": { - "id": "Mm7-fG_LltD7" - }, - "source": [ - "### 🦜🔗 Library Installation\n", - "The integration lives in its own `langchain-google-cloud-sql-pg` package, so we need to install it." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "id": "1VELXvcj8AId", - "metadata": { - "id": "1VELXvcj8AId" - }, - "outputs": [], - "source": [ - "%pip install --upgrade --quiet langchain-google-cloud-sql-pg langchain-google-vertexai" - ] - }, - { - "cell_type": "markdown", - "id": "98TVoM3MNDHu", - "metadata": { - "id": "98TVoM3MNDHu" - }, - "source": [ - "**Colab only:** Uncomment the following cell to restart the kernel or use the button to restart the kernel. For Vertex AI Workbench you can restart the terminal using the button on top." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "id": "v6jBDnYnNM08", - "metadata": { - "id": "v6jBDnYnNM08" - }, - "outputs": [], - "source": [ - "# # Automatically restart kernel after installs so that your environment can access the new packages\n", - "# import IPython\n", - "\n", - "# app = IPython.Application.instance()\n", - "# app.kernel.do_shutdown(True)" - ] - }, - { - "cell_type": "markdown", - "id": "yygMe6rPWxHS", - "metadata": { - "id": "yygMe6rPWxHS" - }, - "source": [ - "### 🔐 Authentication\n", - "Authenticate to Google Cloud as the IAM user logged into this notebook in order to access your Google Cloud Project.\n", - "\n", - "* If you are using Colab to run this notebook, use the cell below and continue.\n", - "* If you are using Vertex AI Workbench, check out the setup instructions [here](https://github.com/GoogleCloudPlatform/generative-ai/tree/main/setup-env)." - ] - }, - { - "cell_type": "code", - "execution_count": 1, - "id": "PTXN1_DSXj2b", - "metadata": { - "id": "PTXN1_DSXj2b" - }, - "outputs": [], - "source": [ - "from google.colab import auth\n", - "\n", - "auth.authenticate_user()" - ] - }, - { - "cell_type": "markdown", - "id": "NEvB9BoLEulY", - "metadata": { - "id": "NEvB9BoLEulY" - }, - "source": [ - "### ☁ Set Your Google Cloud Project\n", - "Set your Google Cloud project so that you can leverage Google Cloud resources within this notebook.\n", - "\n", - "If you don't know your project ID, try the following:\n", - "\n", - "* Run `gcloud config list`.\n", - "* Run `gcloud projects list`.\n", - "* See the support page: [Locate the project ID](https://support.google.com/googleapi/answer/7014113)." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "id": "gfkS3yVRE4_W", - "metadata": { - "cellView": "form", - "id": "gfkS3yVRE4_W" - }, - "outputs": [], - "source": [ - "# @markdown Please fill in the value below with your Google Cloud project ID and then run the cell.\n", - "\n", - "PROJECT_ID = \"my-project-id\" # @param {type:\"string\"}\n", - "\n", - "# Set the project id\n", - "!gcloud config set project {PROJECT_ID}" - ] - }, - { - "cell_type": "markdown", - "id": "rEWWNoNnKOgq", - "metadata": { - "id": "rEWWNoNnKOgq" - }, - "source": [ - "### 💡 API Enablement\n", - "The `langchain-google-cloud-sql-pg` package requires that you [enable the Cloud SQL Admin API](https://console.cloud.google.com/flows/enableapi?apiid=sqladmin.googleapis.com) in your Google Cloud Project." - ] - }, - { - "cell_type": "code", - "execution_count": 3, - "id": "5utKIdq7KYi5", - "metadata": { - "id": "5utKIdq7KYi5" - }, - "outputs": [], - "source": [ - "# enable Cloud SQL Admin API\n", - "!gcloud services enable sqladmin.googleapis.com" - ] - }, - { - "cell_type": "markdown", - "id": "f8f2830ee9ca1e01", - "metadata": { - "id": "f8f2830ee9ca1e01" - }, - "source": [ - "## Basic Usage" - ] - }, - { - "cell_type": "markdown", - "id": "OMvzMWRrR6n7", - "metadata": { - "id": "OMvzMWRrR6n7" - }, - "source": [ - "### Set Cloud SQL database values\n", - "Find your database values, in the [Cloud SQL Instances page](https://console.cloud.google.com/sql?_ga=2.223735448.2062268965.1707700487-2088871159.1707257687)." - ] - }, - { - "cell_type": "code", - "execution_count": 4, - "id": "irl7eMFnSPZr", - "metadata": { - "id": "irl7eMFnSPZr" - }, - "outputs": [], - "source": [ - "# @title Set Your Values Here { display-mode: \"form\" }\n", - "REGION = \"us-central1\" # @param {type: \"string\"}\n", - "INSTANCE = \"my-postgresql-instance\" # @param {type: \"string\"}\n", - "DATABASE = \"my-database\" # @param {type: \"string\"}\n", - "TABLE_NAME = \"message_store\" # @param {type: \"string\"}" - ] - }, - { - "cell_type": "markdown", - "id": "QuQigs4UoFQ2", - "metadata": { - "id": "QuQigs4UoFQ2" - }, - "source": [ - "### PostgresEngine Connection Pool\n", - "\n", - "One of the requirements and arguments to establish Cloud SQL as a ChatMessageHistory memory store is a `PostgresEngine` object. The `PostgresEngine` configures a connection pool to your Cloud SQL database, enabling successful connections from your application and following industry best practices.\n", - "\n", - "To create a `PostgresEngine` using `PostgresEngine.from_instance()` you need to provide only 4 things:\n", - "\n", - "1. `project_id` : Project ID of the Google Cloud Project where the Cloud SQL instance is located.\n", - "1. `region` : Region where the Cloud SQL instance is located.\n", - "1. `instance` : The name of the Cloud SQL instance.\n", - "1. `database` : The name of the database to connect to on the Cloud SQL instance.\n", - "\n", - "By default, [IAM database authentication](https://cloud.google.com/sql/docs/postgres/iam-authentication#iam-db-auth) will be used as the method of database authentication. This library uses the IAM principal belonging to the [Application Default Credentials (ADC)](https://cloud.google.com/docs/authentication/application-default-credentials) sourced from the envionment.\n", - "\n", - "For more informatin on IAM database authentication please see:\n", - "* [Configure an instance for IAM database authentication](https://cloud.google.com/sql/docs/postgres/create-edit-iam-instances)\n", - "* [Manage users with IAM database authentication](https://cloud.google.com/sql/docs/postgres/add-manage-iam-users)\n", - "\n", - "Optionally, [built-in database authentication](https://cloud.google.com/sql/docs/postgres/built-in-authentication) using a username and password to access the Cloud SQL database can also be used. Just provide the optional `user` and `password` arguments to `PostgresEngine.from_instance()`:\n", - "\n", - "* `user` : Database user to use for built-in database authentication and login\n", - "* `password` : Database password to use for built-in database authentication and login.\n" - ] - }, - { - "cell_type": "code", - "execution_count": 5, - "id": "4576e914a866fb40", - "metadata": { - "ExecuteTime": { - "end_time": "2023-08-28T10:04:38.077748Z", - "start_time": "2023-08-28T10:04:36.105894Z" - }, - "id": "4576e914a866fb40", - "jupyter": { - "outputs_hidden": false - } - }, - "outputs": [], - "source": [ - "from langchain_google_cloud_sql_pg import PostgresEngine\n", - "\n", - "engine = PostgresEngine.from_instance(\n", - " project_id=PROJECT_ID, region=REGION, instance=INSTANCE, database=DATABASE\n", - ")" - ] - }, - { - "cell_type": "markdown", - "id": "qPV8WfWr7O54", - "metadata": { - "id": "qPV8WfWr7O54" - }, - "source": [ - "### Initialize a table\n", - "The `PostgresChatMessageHistory` class requires a database table with a specific schema in order to store the chat message history.\n", - "\n", - "The `PostgresEngine` engine has a helper method `init_chat_history_table()` that can be used to create a table with the proper schema for you." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "id": "TEu4VHArRttE", - "metadata": { - "id": "TEu4VHArRttE" - }, - "outputs": [], - "source": [ - "engine.init_chat_history_table(table_name=TABLE_NAME)" - ] - }, - { - "cell_type": "markdown", - "id": "zSYQTYf3UfOi", - "metadata": { - "id": "zSYQTYf3UfOi" - }, - "source": [ - "### PostgresChatMessageHistory\n", - "\n", - "To initialize the `PostgresChatMessageHistory` class you need to provide only 3 things:\n", - "\n", - "1. `engine` - An instance of a `PostgresEngine` engine.\n", - "1. `session_id` - A unique identifier string that specifies an id for the session.\n", - "1. `table_name` : The name of the table within the Cloud SQL database to store the chat message history." - ] - }, - { - "cell_type": "code", - "execution_count": 10, - "id": "Kq7RLtfOq0wi", - "metadata": { - "id": "Kq7RLtfOq0wi" - }, - "outputs": [], - "source": [ - "from langchain_google_cloud_sql_pg import PostgresChatMessageHistory\n", - "\n", - "history = PostgresChatMessageHistory.create_sync(\n", - " engine, session_id=\"test_session\", table_name=TABLE_NAME\n", - ")\n", - "history.add_user_message(\"hi!\")\n", - "history.add_ai_message(\"whats up?\")" - ] - }, - { - "cell_type": "code", - "execution_count": 11, - "id": "b476688cbb32ba90", - "metadata": { - "ExecuteTime": { - "end_time": "2023-08-28T10:04:38.929396Z", - "start_time": "2023-08-28T10:04:38.915727Z" - }, - "colab": { - "base_uri": "https://localhost:8080/" - }, - "id": "b476688cbb32ba90", - "jupyter": { - "outputs_hidden": false - }, - "outputId": "a19e5cd8-4225-476a-d28d-e870c6b838bb" - }, - "outputs": [ - { - "data": { - "text/plain": [ - "[HumanMessage(content='hi!'), AIMessage(content='whats up?')]" - ] - }, - "execution_count": 11, - "metadata": {}, - "output_type": "execute_result" - } - ], - "source": [ - "history.messages" - ] - }, - { - "cell_type": "markdown", - "id": "ss6CbqcTTedr", - "metadata": { - "id": "ss6CbqcTTedr" - }, - "source": [ - "#### Cleaning up\n", - "When the history of a specific session is obsolete and can be deleted, it can be done the following way.\n", - "\n", - "**Note:** Once deleted, the data is no longer stored in Cloud SQL and is gone forever." - ] - }, - { - "cell_type": "code", - "execution_count": 12, - "id": "3khxzFxYO7x6", - "metadata": { - "id": "3khxzFxYO7x6" - }, - "outputs": [], - "source": [ - "history.clear()" - ] - }, - { - "cell_type": "markdown", - "id": "2e5337719d5614fd", - "metadata": { - "id": "2e5337719d5614fd" - }, - "source": [ - "## 🔗 Chaining\n", - "\n", - "We can easily combine this message history class with [LCEL Runnables](/docs/expression_language/how_to/message_history)\n", - "\n", - "To do this we will use one of [Google's Vertex AI chat models](https://python.langchain.com/docs/integrations/chat/google_vertex_ai_palm) which requires that you [enable the Vertex AI API](https://console.cloud.google.com/flows/enableapi?apiid=aiplatform.googleapis.com) in your Google Cloud Project.\n" - ] - }, - { - "cell_type": "code", - "execution_count": 13, - "id": "hYtHM3-TOMCe", - "metadata": { - "id": "hYtHM3-TOMCe" - }, - "outputs": [], - "source": [ - "# enable Vertex AI API\n", - "!gcloud services enable aiplatform.googleapis.com" - ] - }, - { - "cell_type": "code", - "execution_count": 14, - "id": "6558418b-0ece-4d01-9661-56d562d78f7a", - "metadata": { - "id": "6558418b-0ece-4d01-9661-56d562d78f7a" - }, - "outputs": [], - "source": [ - "from langchain_core.prompts import ChatPromptTemplate, MessagesPlaceholder\n", - "from langchain_core.runnables.history import RunnableWithMessageHistory\n", - "from langchain_google_vertexai import ChatVertexAI" - ] - }, - { - "cell_type": "code", - "execution_count": 15, - "id": "82149122-61d3-490d-9bdb-bb98606e8ba1", - "metadata": { - "id": "82149122-61d3-490d-9bdb-bb98606e8ba1" - }, - "outputs": [], - "source": [ - "prompt = ChatPromptTemplate.from_messages(\n", - " [\n", - " (\"system\", \"You are a helpful assistant.\"),\n", - " MessagesPlaceholder(variable_name=\"history\"),\n", - " (\"human\", \"{question}\"),\n", - " ]\n", - ")\n", - "\n", - "chain = prompt | ChatVertexAI(project=PROJECT_ID)" - ] + "cells": [ + { + "cell_type": "markdown", + "id": "f22eab3f84cbeb37", + "metadata": { + "id": "f22eab3f84cbeb37" + }, + "source": [ + "# Google Cloud SQL for PostgreSQL\n", + "\n", + "> [Cloud SQL](https://cloud.google.com/sql) is a fully managed relational database service that offers high performance, seamless integration, and impressive scalability. It offers MySQL, PostgreSQL, and SQL Server database engines. Extend your database application to build AI-powered experiences leveraging Cloud SQL's Langchain integrations.\n", + "\n", + "This notebook goes over how to use `Cloud SQL for PostgreSQL` to store chat message history with the `PostgresChatMessageHistory` class.\n", + "\n", + "Learn more about the package on [GitHub](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/).\n", + "\n", + "[![Open In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/googleapis/langchain-google-cloud-sql-pg-python/blob/main/docs/chat_message_history.ipynb)" + ] + }, + { + "cell_type": "markdown", + "id": "da400c79-a360-43e2-be60-401fd02b2819", + "metadata": { + "id": "da400c79-a360-43e2-be60-401fd02b2819" + }, + "source": [ + "## Before You Begin\n", + "\n", + "To run this notebook, you will need to do the following:\n", + "\n", + " * [Create a Google Cloud Project](https://developers.google.com/workspace/guides/create-project)\n", + " * [Enable the Cloud SQL Admin API.](https://console.cloud.google.com/marketplace/product/google/sqladmin.googleapis.com)\n", + " * [Create a Cloud SQL for PostgreSQL instance](https://cloud.google.com/sql/docs/postgres/create-instance)\n", + " * [Create a Cloud SQL database](https://cloud.google.com/sql/docs/mysql/create-manage-databases)\n", + " * [Add an IAM database user to the database](https://cloud.google.com/sql/docs/postgres/add-manage-iam-users#creating-a-database-user) (Optional)" + ] + }, + { + "cell_type": "markdown", + "id": "Mm7-fG_LltD7", + "metadata": { + "id": "Mm7-fG_LltD7" + }, + "source": [ + "### 🦜🔗 Library Installation\n", + "The integration lives in its own `langchain-google-cloud-sql-pg` package, so we need to install it." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "1VELXvcj8AId", + "metadata": { + "id": "1VELXvcj8AId" + }, + "outputs": [], + "source": [ + "%pip install --upgrade --quiet langchain-google-cloud-sql-pg langchain-google-vertexai" + ] + }, + { + "cell_type": "markdown", + "id": "98TVoM3MNDHu", + "metadata": { + "id": "98TVoM3MNDHu" + }, + "source": [ + "**Colab only:** Uncomment the following cell to restart the kernel or use the button to restart the kernel. For Vertex AI Workbench you can restart the terminal using the button on top." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "v6jBDnYnNM08", + "metadata": { + "id": "v6jBDnYnNM08" + }, + "outputs": [], + "source": [ + "# # Automatically restart kernel after installs so that your environment can access the new packages\n", + "# import IPython\n", + "\n", + "# app = IPython.Application.instance()\n", + "# app.kernel.do_shutdown(True)" + ] + }, + { + "cell_type": "markdown", + "id": "yygMe6rPWxHS", + "metadata": { + "id": "yygMe6rPWxHS" + }, + "source": [ + "### 🔐 Authentication\n", + "Authenticate to Google Cloud as the IAM user logged into this notebook in order to access your Google Cloud Project.\n", + "\n", + "* If you are using Colab to run this notebook, use the cell below and continue.\n", + "* If you are using Vertex AI Workbench, check out the setup instructions [here](https://github.com/GoogleCloudPlatform/generative-ai/tree/main/setup-env)." + ] + }, + { + "cell_type": "code", + "execution_count": 1, + "id": "PTXN1_DSXj2b", + "metadata": { + "id": "PTXN1_DSXj2b" + }, + "outputs": [], + "source": [ + "from google.colab import auth\n", + "\n", + "auth.authenticate_user()" + ] + }, + { + "cell_type": "markdown", + "id": "NEvB9BoLEulY", + "metadata": { + "id": "NEvB9BoLEulY" + }, + "source": [ + "### ☁ Set Your Google Cloud Project\n", + "Set your Google Cloud project so that you can leverage Google Cloud resources within this notebook.\n", + "\n", + "If you don't know your project ID, try the following:\n", + "\n", + "* Run `gcloud config list`.\n", + "* Run `gcloud projects list`.\n", + "* See the support page: [Locate the project ID](https://support.google.com/googleapi/answer/7014113)." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "gfkS3yVRE4_W", + "metadata": { + "cellView": "form", + "id": "gfkS3yVRE4_W" + }, + "outputs": [], + "source": [ + "# @markdown Please fill in the value below with your Google Cloud project ID and then run the cell.\n", + "\n", + "PROJECT_ID = \"my-project-id\" # @param {type:\"string\"}\n", + "\n", + "# Set the project id\n", + "!gcloud config set project {PROJECT_ID}" + ] + }, + { + "cell_type": "markdown", + "id": "rEWWNoNnKOgq", + "metadata": { + "id": "rEWWNoNnKOgq" + }, + "source": [ + "### 💡 API Enablement\n", + "The `langchain-google-cloud-sql-pg` package requires that you [enable the Cloud SQL Admin API](https://console.cloud.google.com/flows/enableapi?apiid=sqladmin.googleapis.com) in your Google Cloud Project." + ] + }, + { + "cell_type": "code", + "execution_count": 3, + "id": "5utKIdq7KYi5", + "metadata": { + "id": "5utKIdq7KYi5" + }, + "outputs": [], + "source": [ + "# enable Cloud SQL Admin API\n", + "!gcloud services enable sqladmin.googleapis.com" + ] + }, + { + "cell_type": "markdown", + "id": "f8f2830ee9ca1e01", + "metadata": { + "id": "f8f2830ee9ca1e01" + }, + "source": [ + "## Basic Usage" + ] + }, + { + "cell_type": "markdown", + "id": "OMvzMWRrR6n7", + "metadata": { + "id": "OMvzMWRrR6n7" + }, + "source": [ + "### Set Cloud SQL database values\n", + "Find your database values, in the [Cloud SQL Instances page](https://console.cloud.google.com/sql?_ga=2.223735448.2062268965.1707700487-2088871159.1707257687)." + ] + }, + { + "cell_type": "code", + "execution_count": 4, + "id": "irl7eMFnSPZr", + "metadata": { + "id": "irl7eMFnSPZr" + }, + "outputs": [], + "source": [ + "# @title Set Your Values Here { display-mode: \"form\" }\n", + "REGION = \"us-central1\" # @param {type: \"string\"}\n", + "INSTANCE = \"my-postgresql-instance\" # @param {type: \"string\"}\n", + "DATABASE = \"my-database\" # @param {type: \"string\"}\n", + "TABLE_NAME = \"message_store\" # @param {type: \"string\"}" + ] + }, + { + "cell_type": "markdown", + "id": "QuQigs4UoFQ2", + "metadata": { + "id": "QuQigs4UoFQ2" + }, + "source": [ + "### PostgresEngine Connection Pool\n", + "\n", + "One of the requirements and arguments to establish Cloud SQL as a ChatMessageHistory memory store is a `PostgresEngine` object. The `PostgresEngine` configures a connection pool to your Cloud SQL database, enabling successful connections from your application and following industry best practices.\n", + "\n", + "To create a `PostgresEngine` using `PostgresEngine.from_instance()` you need to provide only 4 things:\n", + "\n", + "1. `project_id` : Project ID of the Google Cloud Project where the Cloud SQL instance is located.\n", + "1. `region` : Region where the Cloud SQL instance is located.\n", + "1. `instance` : The name of the Cloud SQL instance.\n", + "1. `database` : The name of the database to connect to on the Cloud SQL instance.\n", + "\n", + "By default, [IAM database authentication](https://cloud.google.com/sql/docs/postgres/iam-authentication#iam-db-auth) will be used as the method of database authentication. This library uses the IAM principal belonging to the [Application Default Credentials (ADC)](https://cloud.google.com/docs/authentication/application-default-credentials) sourced from the envionment.\n", + "\n", + "For more informatin on IAM database authentication please see:\n", + "* [Configure an instance for IAM database authentication](https://cloud.google.com/sql/docs/postgres/create-edit-iam-instances)\n", + "* [Manage users with IAM database authentication](https://cloud.google.com/sql/docs/postgres/add-manage-iam-users)\n", + "\n", + "Optionally, [built-in database authentication](https://cloud.google.com/sql/docs/postgres/built-in-authentication) using a username and password to access the Cloud SQL database can also be used. Just provide the optional `user` and `password` arguments to `PostgresEngine.from_instance()`:\n", + "\n", + "* `user` : Database user to use for built-in database authentication and login\n", + "* `password` : Database password to use for built-in database authentication and login.\n" + ] + }, + { + "cell_type": "code", + "execution_count": 5, + "id": "4576e914a866fb40", + "metadata": { + "ExecuteTime": { + "end_time": "2023-08-28T10:04:38.077748Z", + "start_time": "2023-08-28T10:04:36.105894Z" + }, + "id": "4576e914a866fb40", + "jupyter": { + "outputs_hidden": false + } + }, + "outputs": [], + "source": [ + "from langchain_google_cloud_sql_pg import PostgresEngine\n", + "\n", + "engine = PostgresEngine.from_instance(\n", + " project_id=PROJECT_ID, region=REGION, instance=INSTANCE, database=DATABASE\n", + ")" + ] + }, + { + "cell_type": "markdown", + "id": "qPV8WfWr7O54", + "metadata": { + "id": "qPV8WfWr7O54" + }, + "source": [ + "### Initialize a table\n", + "The `PostgresChatMessageHistory` class requires a database table with a specific schema in order to store the chat message history.\n", + "\n", + "The `PostgresEngine` engine has a helper method `init_chat_history_table()` that can be used to create a table with the proper schema for you." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "TEu4VHArRttE", + "metadata": { + "id": "TEu4VHArRttE" + }, + "outputs": [], + "source": [ + "engine.init_chat_history_table(table_name=TABLE_NAME)" + ] + }, + { + "cell_type": "markdown", + "id": "zSYQTYf3UfOi", + "metadata": { + "id": "zSYQTYf3UfOi" + }, + "source": [ + "### PostgresChatMessageHistory\n", + "\n", + "To initialize the `PostgresChatMessageHistory` class you need to provide only 3 things:\n", + "\n", + "1. `engine` - An instance of a `PostgresEngine` engine.\n", + "1. `session_id` - A unique identifier string that specifies an id for the session.\n", + "1. `table_name` : The name of the table within the Cloud SQL database to store the chat message history." + ] + }, + { + "cell_type": "code", + "execution_count": 10, + "id": "Kq7RLtfOq0wi", + "metadata": { + "id": "Kq7RLtfOq0wi" + }, + "outputs": [], + "source": [ + "from langchain_google_cloud_sql_pg import PostgresChatMessageHistory\n", + "\n", + "history = PostgresChatMessageHistory.create_sync(\n", + " engine, session_id=\"test_session\", table_name=TABLE_NAME\n", + ")\n", + "history.add_user_message(\"hi!\")\n", + "history.add_ai_message(\"whats up?\")" + ] + }, + { + "cell_type": "code", + "execution_count": 11, + "id": "b476688cbb32ba90", + "metadata": { + "ExecuteTime": { + "end_time": "2023-08-28T10:04:38.929396Z", + "start_time": "2023-08-28T10:04:38.915727Z" }, - { - "cell_type": "code", - "execution_count": 16, - "id": "2df90853-b67c-490f-b7f8-b69d69270b9c", - "metadata": { - "id": "2df90853-b67c-490f-b7f8-b69d69270b9c" - }, - "outputs": [], - "source": [ - "chain_with_history = RunnableWithMessageHistory(\n", - " chain,\n", - " lambda session_id: PostgresChatMessageHistory.create_sync(\n", - " engine,\n", - " session_id=session_id,\n", - " table_name=TABLE_NAME,\n", - " ),\n", - " input_messages_key=\"question\",\n", - " history_messages_key=\"history\",\n", - ")" - ] + "colab": { + "base_uri": "https://localhost:8080/" }, - { - "cell_type": "code", - "execution_count": 17, - "id": "0ce596b8-3b78-48fd-9f92-46dccbbfd58b", - "metadata": { - "id": "0ce596b8-3b78-48fd-9f92-46dccbbfd58b" - }, - "outputs": [], - "source": [ - "# This is where we configure the session id\n", - "config = {\"configurable\": {\"session_id\": \"test_session\"}}" - ] + "id": "b476688cbb32ba90", + "jupyter": { + "outputs_hidden": false }, + "outputId": "a19e5cd8-4225-476a-d28d-e870c6b838bb" + }, + "outputs": [ { - "cell_type": "code", - "execution_count": 18, - "id": "38e1423b-ba86-4496-9151-25932fab1a8b", - "metadata": { - "colab": { - "base_uri": "https://localhost:8080/" - }, - "id": "38e1423b-ba86-4496-9151-25932fab1a8b", - "outputId": "d5c93570-4b0b-4fe8-d19c-4b361fe74291" - }, - "outputs": [ - { - "data": { - "text/plain": [ - "AIMessage(content=' Hello Bob, how can I help you today?')" - ] - }, - "execution_count": 18, - "metadata": {}, - "output_type": "execute_result" - } - ], - "source": [ - "chain_with_history.invoke({\"question\": \"Hi! I'm bob\"}, config=config)" + "data": { + "text/plain": [ + "[HumanMessage(content='hi!'), AIMessage(content='whats up?')]" ] + }, + "execution_count": 11, + "metadata": {}, + "output_type": "execute_result" + } + ], + "source": [ + "history.messages" + ] + }, + { + "cell_type": "markdown", + "id": "ss6CbqcTTedr", + "metadata": { + "id": "ss6CbqcTTedr" + }, + "source": [ + "#### Cleaning up\n", + "When the history of a specific session is obsolete and can be deleted, it can be done the following way.\n", + "\n", + "**Note:** Once deleted, the data is no longer stored in Cloud SQL and is gone forever." + ] + }, + { + "cell_type": "code", + "execution_count": 12, + "id": "3khxzFxYO7x6", + "metadata": { + "id": "3khxzFxYO7x6" + }, + "outputs": [], + "source": [ + "history.clear()" + ] + }, + { + "cell_type": "markdown", + "id": "2e5337719d5614fd", + "metadata": { + "id": "2e5337719d5614fd" + }, + "source": [ + "## 🔗 Chaining\n", + "\n", + "We can easily combine this message history class with [LCEL Runnables](/docs/expression_language/how_to/message_history)\n", + "\n", + "To do this we will use one of [Google's Vertex AI chat models](https://python.langchain.com/docs/integrations/chat/google_vertex_ai_palm) which requires that you [enable the Vertex AI API](https://console.cloud.google.com/flows/enableapi?apiid=aiplatform.googleapis.com) in your Google Cloud Project.\n" + ] + }, + { + "cell_type": "code", + "execution_count": 13, + "id": "hYtHM3-TOMCe", + "metadata": { + "id": "hYtHM3-TOMCe" + }, + "outputs": [], + "source": [ + "# enable Vertex AI API\n", + "!gcloud services enable aiplatform.googleapis.com" + ] + }, + { + "cell_type": "code", + "execution_count": 14, + "id": "6558418b-0ece-4d01-9661-56d562d78f7a", + "metadata": { + "id": "6558418b-0ece-4d01-9661-56d562d78f7a" + }, + "outputs": [], + "source": [ + "from langchain_core.prompts import ChatPromptTemplate, MessagesPlaceholder\n", + "from langchain_core.runnables.history import RunnableWithMessageHistory\n", + "from langchain_google_vertexai import ChatVertexAI" + ] + }, + { + "cell_type": "code", + "execution_count": 15, + "id": "82149122-61d3-490d-9bdb-bb98606e8ba1", + "metadata": { + "id": "82149122-61d3-490d-9bdb-bb98606e8ba1" + }, + "outputs": [], + "source": [ + "prompt = ChatPromptTemplate.from_messages(\n", + " [\n", + " (\"system\", \"You are a helpful assistant.\"),\n", + " MessagesPlaceholder(variable_name=\"history\"),\n", + " (\"human\", \"{question}\"),\n", + " ]\n", + ")\n", + "\n", + "chain = prompt | ChatVertexAI(project=PROJECT_ID)" + ] + }, + { + "cell_type": "code", + "execution_count": 16, + "id": "2df90853-b67c-490f-b7f8-b69d69270b9c", + "metadata": { + "id": "2df90853-b67c-490f-b7f8-b69d69270b9c" + }, + "outputs": [], + "source": [ + "chain_with_history = RunnableWithMessageHistory(\n", + " chain,\n", + " lambda session_id: PostgresChatMessageHistory.create_sync(\n", + " engine,\n", + " session_id=session_id,\n", + " table_name=TABLE_NAME,\n", + " ),\n", + " input_messages_key=\"question\",\n", + " history_messages_key=\"history\",\n", + ")" + ] + }, + { + "cell_type": "code", + "execution_count": 17, + "id": "0ce596b8-3b78-48fd-9f92-46dccbbfd58b", + "metadata": { + "id": "0ce596b8-3b78-48fd-9f92-46dccbbfd58b" + }, + "outputs": [], + "source": [ + "# This is where we configure the session id\n", + "config = {\"configurable\": {\"session_id\": \"test_session\"}}" + ] + }, + { + "cell_type": "code", + "execution_count": 18, + "id": "38e1423b-ba86-4496-9151-25932fab1a8b", + "metadata": { + "colab": { + "base_uri": "https://localhost:8080/" }, + "id": "38e1423b-ba86-4496-9151-25932fab1a8b", + "outputId": "d5c93570-4b0b-4fe8-d19c-4b361fe74291" + }, + "outputs": [ { - "cell_type": "code", - "execution_count": 19, - "id": "2ee4ee62-a216-4fb1-bf33-57476a84cf16", - "metadata": { - "colab": { - "base_uri": "https://localhost:8080/" - }, - "id": "2ee4ee62-a216-4fb1-bf33-57476a84cf16", - "outputId": "288fe388-3f60-41b8-8edb-37cfbec18981" - }, - "outputs": [ - { - "data": { - "text/plain": [ - "AIMessage(content=' Your name is Bob.')" - ] - }, - "execution_count": 19, - "metadata": {}, - "output_type": "execute_result" - } - ], - "source": [ - "chain_with_history.invoke({\"question\": \"Whats my name\"}, config=config)" + "data": { + "text/plain": [ + "AIMessage(content=' Hello Bob, how can I help you today?')" ] + }, + "execution_count": 18, + "metadata": {}, + "output_type": "execute_result" } - ], - "metadata": { + ], + "source": [ + "chain_with_history.invoke({\"question\": \"Hi! I'm bob\"}, config=config)" + ] + }, + { + "cell_type": "code", + "execution_count": 19, + "id": "2ee4ee62-a216-4fb1-bf33-57476a84cf16", + "metadata": { "colab": { - "provenance": [], - "toc_visible": true - }, - "kernelspec": { - "display_name": "Python 3 (ipykernel)", - "language": "python", - "name": "python3" + "base_uri": "https://localhost:8080/" }, - "language_info": { - "codemirror_mode": { - "name": "ipython", - "version": 3 - }, - "file_extension": ".py", - "mimetype": "text/x-python", - "name": "python", - "nbconvert_exporter": "python", - "pygments_lexer": "ipython3", - "version": "3.8.8" + "id": "2ee4ee62-a216-4fb1-bf33-57476a84cf16", + "outputId": "288fe388-3f60-41b8-8edb-37cfbec18981" + }, + "outputs": [ + { + "data": { + "text/plain": [ + "AIMessage(content=' Your name is Bob.')" + ] + }, + "execution_count": 19, + "metadata": {}, + "output_type": "execute_result" } + ], + "source": [ + "chain_with_history.invoke({\"question\": \"Whats my name\"}, config=config)" + ] + } + ], + "metadata": { + "colab": { + "provenance": [], + "toc_visible": true + }, + "kernelspec": { + "display_name": "Python 3 (ipykernel)", + "language": "python", + "name": "python3" }, - "nbformat": 4, - "nbformat_minor": 5 -} \ No newline at end of file + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.8.8" + } + }, + "nbformat": 4, + "nbformat_minor": 5 +} diff --git a/docs/document_loader.ipynb b/docs/document_loader.ipynb index 241ce919..a40123fe 100644 --- a/docs/document_loader.ipynb +++ b/docs/document_loader.ipynb @@ -1,381 +1,362 @@ { - "cells": [ - { - "cell_type": "markdown", - "metadata": { - "id": "E_RJy7C1bpCT" - }, - "source": [ - "# Cloud SQL for PostgreSQL\n", - "\n", - "> [Cloud SQL for PostgreSQL](https://cloud.google.com/sql/docs/postgres) is a fully-managed database service that helps you set up, maintain, manage, and administer your PostgreSQL relational databases on Google Cloud Platform. Extend your database application to build AI-powered experiences leveraging Cloud SQL for PostgreSQL's Langchain integrations.\n", - "\n", - "This notebook goes over how to use `Cloud SQL for PostgreSQL` to load Documents with the `PostgresLoader` class." - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "xjcxaw6--Xyy" - }, - "source": [ - "## Before you begin\n", - "\n", - "To run this notebook, you will need to do the following:\n", - " * [Create a Google Cloud Project](https://developers.google.com/workspace/guides/create-project)\n", - " * [Enable the Cloud SQL Admin API.](https://console.cloud.google.com/marketplace/product/google/sqladmin.googleapis.com)\n", - " * [Create a Cloud SQL for PostgreSQL instance.](https://cloud.google.com/sql/docs/postgres/create-instance)\n", - " * [Create a Cloud SQL for PostgreSQL database.](https://cloud.google.com/sql/docs/postgres/create-manage-databases)\n", - " * [Add a User to the database.](https://cloud.google.com/sql/docs/postgres/create-manage-users)" - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "IR54BmgvdHT_" - }, - "source": [ - "### 🦜🔗 Library Installation\n", - "Install the integration library, `langchain_google_cloud_sql_pg`." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": { - "colab": { - "base_uri": "https://localhost:8080/", - "height": 1000 - }, - "id": "0ZITIDE160OD", - "outputId": "90e0636e-ff34-4e1e-ad37-d2a6db4a317e" - }, - "outputs": [], - "source": [ - "%pip install --upgrade --quiet langchain_google_cloud_sql_pg" - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "v40bB_GMcr9f" - }, - "source": [ - "**Colab only:** Uncomment the following cell to restart the kernel or use the button to restart the kernel. For Vertex AI Workbench you can restart the terminal using the button on top." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": { - "id": "6o0iGVIdDD6K" - }, - "outputs": [], - "source": [ - "# # Automatically restart kernel after installs so that your environment can access the new packages\n", - "# import IPython\n", - "\n", - "# app = IPython.Application.instance()\n", - "# app.kernel.do_shutdown(True)" - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "cTXTbj4UltKf" - }, - "source": [ - "### 🔐 Authentication\n", - "Authenticate to Google Cloud as the IAM user logged into this notebook in order to access your Google Cloud Project.\n", - "\n", - "* If you are using Colab to run this notebook, use the cell below and continue.\n", - "* If you are using Vertex AI Workbench, check out the setup instructions [here](https://github.com/GoogleCloudPlatform/generative-ai/tree/main/setup-env)." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "from google.colab import auth\n", - "\n", - "auth.authenticate_user()" - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "Uj02bMRAc9_c" - }, - "source": [ - "### ☁ Set Your Google Cloud Project\n", - "Set your Google Cloud project so that you can leverage Google Cloud resources within this notebook.\n", - "\n", - "If you don't know your project ID, try the following:\n", - "\n", - "* Run `gcloud config list`.\n", - "* Run `gcloud projects list`.\n", - "* See the support page: [Locate the project ID](https://support.google.com/googleapi/answer/7014113)." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": { - "colab": { - "base_uri": "https://localhost:8080/" - }, - "id": "wnp1R1PYc9_c", - "outputId": "6502c721-a2fd-451f-b946-9f7b850d5966" - }, - "outputs": [], - "source": [ - "# @title Project { display-mode: \"form\" }\n", - "PROJECT_ID = \"gcp_project_id\" # @param {type:\"string\"}\n", - "\n", - "# Set the project id\n", - "! gcloud config set project {PROJECT_ID}" - ] - }, - { - "cell_type": "markdown", - "id": "rEWWNoNnKOgq", - "metadata": { - "id": "rEWWNoNnKOgq" - }, - "source": [ - "### 💡 API Enablement\n", - "The `langchain_google_cloud_sql_pg` package requires that you [enable the Cloud SQL Admin API](https://console.cloud.google.com/flows/enableapi?apiid=sqladmin.googleapis.com) in your Google Cloud Project." - ] - }, - { - "cell_type": "code", - "execution_count": 3, - "id": "5utKIdq7KYi5", - "metadata": { - "id": "5utKIdq7KYi5" - }, - "outputs": [], - "source": [ - "# enable Cloud SQL Admin API\n", - "!gcloud services enable sqladmin.googleapis.com" - ] - }, - { - "cell_type": "markdown", - "id": "f8f2830ee9ca1e01", - "metadata": { - "id": "f8f2830ee9ca1e01" - }, - "source": [ - "## Basic Usage" - ] - }, - { - "cell_type": "markdown", - "id": "OMvzMWRrR6n7", - "metadata": { - "id": "OMvzMWRrR6n7" - }, - "source": [ - "### Set Cloud SQL database values\n", - "Find your database variables, in the [Cloud SQL Instances page](https://console.cloud.google.com/sql/instances)." - ] - }, - { - "cell_type": "code", - "execution_count": 4, - "id": "irl7eMFnSPZr", - "metadata": { - "id": "irl7eMFnSPZr" - }, - "outputs": [], - "source": [ - "# @title Set Your Values Here { display-mode: \"form\" }\n", - "REGION = \"us-central1\" # @param {type: \"string\"}\n", - "INSTANCE = \"my-primary\" # @param {type: \"string\"}\n", - "DATABASE = \"my-database\" # @param {type: \"string\"}\n", - "TABLE_NAME = \"vector_store\" # @param {type: \"string\"}" - ] - }, - { - "cell_type": "markdown", - "id": "QuQigs4UoFQ2", - "metadata": { - "id": "QuQigs4UoFQ2" - }, - "source": [ - "### Cloud SQL Engine\n", - "\n", - "One of the requirements and arguments to establish PostgreSQL as a document loader is a `PostgresEngine` object. The `PostgresEngine` configures a connection pool to your Cloud SQL for PostgreSQL database, enabling successful connections from your application and following industry best practices.\n", - "\n", - "To create a `PostgresEngine` using `PostgresEngine.from_instance()` you need to provide only 4 things:\n", - "\n", - "1. `project_id` : Project ID of the Google Cloud Project where the Cloud SQL instance is located.\n", - "1. `region` : Region where the Cloud SQL instance is located.\n", - "1. `instance` : The name of the Cloud SQL instance.\n", - "1. `database` : The name of the database to connect to on the Cloud SQL instance.\n", - "\n", - "By default, [IAM database authentication](https://cloud.google.com/sql/docs/postgres/iam-authentication) will be used as the method of database authentication. This library uses the IAM principal belonging to the [Application Default Credentials (ADC)](https://cloud.google.com/docs/authentication/application-default-credentials) sourced from the environment.\n", - "\n", - "Optionally, [built-in database authentication](https://cloud.google.com/sql/docs/postgres/users) using a username and password to access the Cloud SQL database can also be used. Just provide the optional `user` and `password` arguments to `PostgresEngine.from_instance()`:\n", - "\n", - "* `user` : Database user to use for built-in database authentication and login\n", - "* `password` : Database password to use for built-in database authentication and login.\n" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "**Note**: This tutorial demonstrates the async interface. All async methods have corresponding sync methods." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "from langchain_google_cloud_sql_pg import PostgresEngine\n", - "\n", - "engine = await PostgresEngine.afrom_instance(\n", - " project_id=PROJECT_ID,\n", - " region=REGION,\n", - " instance=INSTANCE,\n", - " database=DATABASE,\n", - ")" - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "e1tl0aNx7SWy" - }, - "source": [ - "### Create PostgresLoader" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": { - "id": "z-AZyzAQ7bsf" - }, - "outputs": [], - "source": [ - "from langchain_google_cloud_sql_pg import PostgresLoader\n", - "\n", - "# Creating a basic PostgreSQL object\n", - "loader = await PostgresLoader.create(engine, table_name=TABLE_NAME)" - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "PeOMpftjc9_e" - }, - "source": [ - "### Load Documents via default table\n", - "The loader returns a list of Documents from the table using the first column as page_content and all other columns as metadata. The default table will have the first column as\n", - "page_content and the second column as metadata (JSON). Each row becomes a document. Please note that if you want your documents to have ids you will need to add them in." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": { - "id": "cwvi_O5Wc9_e" - }, - "outputs": [], - "source": [ - "from langchain_google_cloud_sql_pg import PostgresLoader\n", - "\n", - "# Creating a basic PostgresLoader object\n", - "loader = await PostgresLoader.create(engine, table_name=TABLE_NAME)\n", - "\n", - "docs = await loader.aload()\n", - "print(docs)" - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "kSkL9l1Hc9_e" - }, - "source": [ - "### Load documents via custom table/metadata or custom page content columns" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "loader = await PostgresLoader.create(\n", - " engine,\n", - " table_name=TABLE_NAME,\n", - " content_columns=[\"product_name\"], # Optional\n", - " metadata_columns=[\"id\"], # Optional\n", - ")\n", - "docs = await loader.aload()\n", - "print(docs)" - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "5R6h0_Cvc9_f" - }, - "source": [ - "### Set page content format\n", - "The loader returns a list of Documents, with one document per row, with page content in specified string format, i.e. text (space separated concatenation), JSON, YAML, CSV, etc. JSON and YAML formats include headers, while text and CSV do not include field headers.\n" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": { - "id": "NGNdS7cqc9_f" - }, - "outputs": [], - "source": [ - "loader = await PostgresLoader.create(\n", - " engine,\n", - " table_name=\"products\",\n", - " content_columns=[\"product_name\", \"description\"],\n", - " format=\"YAML\",\n", - ")\n", - "docs = await loader.aload()\n", - "print(docs)" - ] - } - ], - "metadata": { + "cells": [ + { + "cell_type": "markdown", + "metadata": { + "id": "E_RJy7C1bpCT" + }, + "source": [ + "# Google Cloud SQL for PostgreSQL\n", + "\n", + "> [Cloud SQL for PostgreSQL](https://cloud.google.com/sql/docs/postgres) is a fully-managed database service that helps you set up, maintain, manage, and administer your PostgreSQL relational databases on Google Cloud Platform. Extend your database application to build AI-powered experiences leveraging Cloud SQL for PostgreSQL's Langchain integrations.\n", + "\n", + "This notebook goes over how to use `Cloud SQL for PostgreSQL` to load Documents with the `PostgresLoader` class.\n", + "\n", + "Learn more about the package on [GitHub](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/).\n", + "\n", + "[![Open In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/googleapis/langchain-google-cloud-sql-pg-python/blob/main/docs/document_loader.ipynb)" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "xjcxaw6--Xyy" + }, + "source": [ + "## Before you begin\n", + "\n", + "To run this notebook, you will need to do the following:\n", + "\n", + " * [Create a Google Cloud Project](https://developers.google.com/workspace/guides/create-project)\n", + " * [Enable the Cloud SQL Admin API.](https://console.cloud.google.com/marketplace/product/google/sqladmin.googleapis.com)\n", + " * [Create a Cloud SQL for PostgreSQL instance.](https://cloud.google.com/sql/docs/postgres/create-instance)\n", + " * [Create a Cloud SQL for PostgreSQL database.](https://cloud.google.com/sql/docs/postgres/create-manage-databases)\n", + " * [Add a User to the database.](https://cloud.google.com/sql/docs/postgres/create-manage-users)" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "IR54BmgvdHT_" + }, + "source": [ + "### 🦜🔗 Library Installation\n", + "Install the integration library, `langchain_google_cloud_sql_pg`." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": { "colab": { - "provenance": [], - "toc_visible": true + "base_uri": "https://localhost:8080/", + "height": 1000 }, - "kernelspec": { - "display_name": "Python 3 (ipykernel)", - "language": "python", - "name": "python3" + "id": "0ZITIDE160OD", + "outputId": "90e0636e-ff34-4e1e-ad37-d2a6db4a317e" + }, + "outputs": [], + "source": [ + "%pip install --upgrade --quiet langchain_google_cloud_sql_pg" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "v40bB_GMcr9f" + }, + "source": [ + "**Colab only:** Uncomment the following cell to restart the kernel or use the button to restart the kernel. For Vertex AI Workbench you can restart the terminal using the button on top." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": { + "id": "6o0iGVIdDD6K" + }, + "outputs": [], + "source": [ + "# # Automatically restart kernel after installs so that your environment can access the new packages\n", + "# import IPython\n", + "\n", + "# app = IPython.Application.instance()\n", + "# app.kernel.do_shutdown(True)" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "cTXTbj4UltKf" + }, + "source": [ + "### 🔐 Authentication\n", + "Authenticate to Google Cloud as the IAM user logged into this notebook in order to access your Google Cloud Project.\n", + "\n", + "* If you are using Colab to run this notebook, use the cell below and continue.\n", + "* If you are using Vertex AI Workbench, check out the setup instructions [here](https://github.com/GoogleCloudPlatform/generative-ai/tree/main/setup-env)." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "from google.colab import auth\n", + "\n", + "auth.authenticate_user()" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "Uj02bMRAc9_c" + }, + "source": [ + "### ☁ Set Your Google Cloud Project\n", + "Set your Google Cloud project so that you can leverage Google Cloud resources within this notebook.\n", + "\n", + "If you don't know your project ID, try the following:\n", + "\n", + "* Run `gcloud config list`.\n", + "* Run `gcloud projects list`.\n", + "* See the support page: [Locate the project ID](https://support.google.com/googleapi/answer/7014113)." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": { + "colab": { + "base_uri": "https://localhost:8080/" }, - "language_info": { - "codemirror_mode": { - "name": "ipython", - "version": 3 - }, - "file_extension": ".py", - "mimetype": "text/x-python", - "name": "python", - "nbconvert_exporter": "python", - "pygments_lexer": "ipython3", - "version": "3.9.6" - } + "id": "wnp1R1PYc9_c", + "outputId": "6502c721-a2fd-451f-b946-9f7b850d5966" + }, + "outputs": [], + "source": [ + "# @title Project { display-mode: \"form\" }\n", + "PROJECT_ID = \"gcp_project_id\" # @param {type:\"string\"}\n", + "\n", + "# Set the project id\n", + "! gcloud config set project {PROJECT_ID}" + ] + }, + { + "cell_type": "markdown", + "id": "f8f2830ee9ca1e01", + "metadata": { + "id": "f8f2830ee9ca1e01" + }, + "source": [ + "## Basic Usage" + ] + }, + { + "cell_type": "markdown", + "id": "OMvzMWRrR6n7", + "metadata": { + "id": "OMvzMWRrR6n7" + }, + "source": [ + "### Set Cloud SQL database values\n", + "Find your database variables, in the [Cloud SQL Instances page](https://console.cloud.google.com/sql/instances)." + ] + }, + { + "cell_type": "code", + "execution_count": 4, + "id": "irl7eMFnSPZr", + "metadata": { + "id": "irl7eMFnSPZr" + }, + "outputs": [], + "source": [ + "# @title Set Your Values Here { display-mode: \"form\" }\n", + "REGION = \"us-central1\" # @param {type: \"string\"}\n", + "INSTANCE = \"my-primary\" # @param {type: \"string\"}\n", + "DATABASE = \"my-database\" # @param {type: \"string\"}\n", + "TABLE_NAME = \"vector_store\" # @param {type: \"string\"}" + ] + }, + { + "cell_type": "markdown", + "id": "QuQigs4UoFQ2", + "metadata": { + "id": "QuQigs4UoFQ2" + }, + "source": [ + "### Cloud SQL Engine\n", + "\n", + "One of the requirements and arguments to establish PostgreSQL as a document loader is a `PostgresEngine` object. The `PostgresEngine` configures a connection pool to your Cloud SQL for PostgreSQL database, enabling successful connections from your application and following industry best practices.\n", + "\n", + "To create a `PostgresEngine` using `PostgresEngine.from_instance()` you need to provide only 4 things:\n", + "\n", + "1. `project_id` : Project ID of the Google Cloud Project where the Cloud SQL instance is located.\n", + "1. `region` : Region where the Cloud SQL instance is located.\n", + "1. `instance` : The name of the Cloud SQL instance.\n", + "1. `database` : The name of the database to connect to on the Cloud SQL instance.\n", + "\n", + "By default, [IAM database authentication](https://cloud.google.com/sql/docs/postgres/iam-authentication) will be used as the method of database authentication. This library uses the IAM principal belonging to the [Application Default Credentials (ADC)](https://cloud.google.com/docs/authentication/application-default-credentials) sourced from the environment.\n", + "\n", + "Optionally, [built-in database authentication](https://cloud.google.com/sql/docs/postgres/users) using a username and password to access the Cloud SQL database can also be used. Just provide the optional `user` and `password` arguments to `PostgresEngine.from_instance()`:\n", + "\n", + "* `user` : Database user to use for built-in database authentication and login\n", + "* `password` : Database password to use for built-in database authentication and login.\n" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "**Note**: This tutorial demonstrates the async interface. All async methods have corresponding sync methods." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "from langchain_google_cloud_sql_pg import PostgresEngine\n", + "\n", + "engine = await PostgresEngine.afrom_instance(\n", + " project_id=PROJECT_ID,\n", + " region=REGION,\n", + " instance=INSTANCE,\n", + " database=DATABASE,\n", + ")" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "e1tl0aNx7SWy" + }, + "source": [ + "### Create PostgresLoader" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": { + "id": "z-AZyzAQ7bsf" + }, + "outputs": [], + "source": [ + "from langchain_google_cloud_sql_pg import PostgresLoader\n", + "\n", + "# Creating a basic PostgreSQL object\n", + "loader = await PostgresLoader.create(engine, table_name=TABLE_NAME)" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "PeOMpftjc9_e" + }, + "source": [ + "### Load Documents via default table\n", + "The loader returns a list of Documents from the table using the first column as page_content and all other columns as metadata. The default table will have the first column as\n", + "page_content and the second column as metadata (JSON). Each row becomes a document. Please note that if you want your documents to have ids you will need to add them in." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": { + "id": "cwvi_O5Wc9_e" + }, + "outputs": [], + "source": [ + "from langchain_google_cloud_sql_pg import PostgresLoader\n", + "\n", + "# Creating a basic PostgresLoader object\n", + "loader = await PostgresLoader.create(engine, table_name=TABLE_NAME)\n", + "\n", + "docs = await loader.aload()\n", + "print(docs)" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "kSkL9l1Hc9_e" + }, + "source": [ + "### Load documents via custom table/metadata or custom page content columns" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "loader = await PostgresLoader.create(\n", + " engine,\n", + " table_name=TABLE_NAME,\n", + " content_columns=[\"product_name\"], # Optional\n", + " metadata_columns=[\"id\"], # Optional\n", + ")\n", + "docs = await loader.aload()\n", + "print(docs)" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "5R6h0_Cvc9_f" + }, + "source": [ + "### Set page content format\n", + "The loader returns a list of Documents, with one document per row, with page content in specified string format, i.e. text (space separated concatenation), JSON, YAML, CSV, etc. JSON and YAML formats include headers, while text and CSV do not include field headers.\n" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": { + "id": "NGNdS7cqc9_f" + }, + "outputs": [], + "source": [ + "loader = await PostgresLoader.create(\n", + " engine,\n", + " table_name=\"products\",\n", + " content_columns=[\"product_name\", \"description\"],\n", + " format=\"YAML\",\n", + ")\n", + "docs = await loader.aload()\n", + "print(docs)" + ] + } + ], + "metadata": { + "colab": { + "provenance": [], + "toc_visible": true + }, + "kernelspec": { + "display_name": "Python 3 (ipykernel)", + "language": "python", + "name": "python3" }, - "nbformat": 4, - "nbformat_minor": 4 + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.9.6" + } + }, + "nbformat": 4, + "nbformat_minor": 4 } \ No newline at end of file diff --git a/docs/vector_store.ipynb b/docs/vector_store.ipynb index 2cab5c25..eb4fa871 100644 --- a/docs/vector_store.ipynb +++ b/docs/vector_store.ipynb @@ -1,567 +1,548 @@ { - "cells": [ - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "# Cloud SQL for PostgreSQL\n", - "\n", - "> [Cloud SQL](https://cloud.google.com/sql) is a fully managed relational database service that offers high performance, seamless integration, and impressive scalability. It offers PostgreSQL, PostgreSQL, and SQL Server database engines. Extend your database application to build AI-powered experiences leveraging Cloud SQL's Langchain integrations.\n", - "\n", - "This notebook goes over how to use `Cloud SQL for PostgreSQL` to store vector embeddings with the `PostgresVectorStore` class." - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "## Before you begin\n", - "\n", - "To run this notebook, you will need to do the following:\n", - " * [Create a Google Cloud Project](https://developers.google.com/workspace/guides/create-project)\n", - " * [Enable the Cloud SQL Admin API.](https://console.cloud.google.com/flows/enableapi?apiid=sqladmin.googleapis.com)\n", - " * [Create a Cloud SQL instance.](https://cloud.google.com/sql/docs/postgres/connect-instance-auth-proxy#create-instance)\n", - " * [Create a Cloud SQL database.](https://cloud.google.com/sql/docs/postgres/create-manage-databases)\n", - " * [Add a User to the database.](https://cloud.google.com/sql/docs/postgres/create-manage-users)" - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "IR54BmgvdHT_" - }, - "source": [ - "### 🦜🔗 Library Installation\n", - "Install the integration library, `langchain-google-cloud-sql-pg`, and the library for the embedding service, `langchain-google-vertexai`." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": { - "colab": { - "base_uri": "https://localhost:8080/", - "height": 1000 - }, - "id": "0ZITIDE160OD", - "outputId": "e184bc0d-6541-4e0a-82d2-1e216db00a2d" - }, - "outputs": [], - "source": [ - "%pip install --upgrade --quiet langchain-google-cloud-sql-pg langchain-google-vertexai" - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "v40bB_GMcr9f" - }, - "source": [ - "**Colab only:** Uncomment the following cell to restart the kernel or use the button to restart the kernel. For Vertex AI Workbench you can restart the terminal using the button on top." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "id": "v6jBDnYnNM08", - "metadata": { - "id": "v6jBDnYnNM08" - }, - "outputs": [], - "source": [ - "# # Automatically restart kernel after installs so that your environment can access the new packages\n", - "# import IPython\n", - "\n", - "# app = IPython.Application.instance()\n", - "# app.kernel.do_shutdown(True)" - ] - }, - { - "cell_type": "markdown", - "id": "yygMe6rPWxHS", - "metadata": { - "id": "yygMe6rPWxHS" - }, - "source": [ - "### 🔐 Authentication\n", - "Authenticate to Google Cloud as the IAM user logged into this notebook in order to access your Google Cloud Project.\n", - "\n", - "* If you are using Colab to run this notebook, use the cell below and continue.\n", - "* If you are using Vertex AI Workbench, check out the setup instructions [here](https://github.com/GoogleCloudPlatform/generative-ai/tree/main/setup-env)." - ] - }, - { - "cell_type": "code", - "execution_count": 1, - "id": "PTXN1_DSXj2b", - "metadata": { - "id": "PTXN1_DSXj2b" - }, - "outputs": [], - "source": [ - "from google.colab import auth\n", - "\n", - "auth.authenticate_user()" - ] - }, - { - "cell_type": "markdown", - "id": "NEvB9BoLEulY", - "metadata": { - "id": "NEvB9BoLEulY" - }, - "source": [ - "### ☁ Set Your Google Cloud Project\n", - "Set your Google Cloud project so that you can leverage Google Cloud resources within this notebook.\n", - "\n", - "If you don't know your project ID, try the following:\n", - "\n", - "* Run `gcloud config list`.\n", - "* Run `gcloud projects list`.\n", - "* See the support page: [Locate the project ID](https://support.google.com/googleapi/answer/7014113)." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "id": "gfkS3yVRE4_W", - "metadata": { - "cellView": "form", - "id": "gfkS3yVRE4_W" - }, - "outputs": [], - "source": [ - "# @markdown Please fill in the value below with your Google Cloud project ID and then run the cell.\n", - "\n", - "PROJECT_ID = \"my-project-id\" # @param {type:\"string\"}\n", - "\n", - "# Set the project id\n", - "!gcloud config set project {PROJECT_ID}" - ] - }, - { - "cell_type": "markdown", - "id": "rEWWNoNnKOgq", - "metadata": { - "id": "rEWWNoNnKOgq" - }, - "source": [ - "### 💡 API Enablement\n", - "The `langchain-google-cloud-sql-pg` package requires that you [enable the Cloud SQL Admin API](https://console.cloud.google.com/flows/enableapi?apiid=sqladmin.googleapis.com) in your Google Cloud Project." - ] - }, - { - "cell_type": "code", - "execution_count": 3, - "id": "5utKIdq7KYi5", - "metadata": { - "id": "5utKIdq7KYi5" - }, - "outputs": [], - "source": [ - "# enable Cloud SQL Admin API\n", - "!gcloud services enable sqladmin.googleapis.com" - ] - }, - { - "cell_type": "markdown", - "id": "f8f2830ee9ca1e01", - "metadata": { - "id": "f8f2830ee9ca1e01" - }, - "source": [ - "## Basic Usage" - ] - }, - { - "cell_type": "markdown", - "id": "OMvzMWRrR6n7", - "metadata": { - "id": "OMvzMWRrR6n7" - }, - "source": [ - "### Set Cloud SQL database values\n", - "Find your database values, in the [Cloud SQL Instances page](https://console.cloud.google.com/sql?_ga=2.223735448.2062268965.1707700487-2088871159.1707257687)." - ] - }, - { - "cell_type": "code", - "execution_count": 4, - "id": "irl7eMFnSPZr", - "metadata": { - "id": "irl7eMFnSPZr" - }, - "outputs": [], - "source": [ - "# @title Set Your Values Here { display-mode: \"form\" }\n", - "REGION = \"us-central1\" # @param {type: \"string\"}\n", - "INSTANCE = \"my-pg-instance\" # @param {type: \"string\"}\n", - "DATABASE = \"my-database\" # @param {type: \"string\"}\n", - "TABLE_NAME = \"vector_store\" # @param {type: \"string\"}" - ] - }, - { - "cell_type": "markdown", - "id": "QuQigs4UoFQ2", - "metadata": { - "id": "QuQigs4UoFQ2" - }, - "source": [ - "### PostgresEngine Connection Pool\n", - "\n", - "One of the requirements and arguments to establish Cloud SQL as a vector store is a `PostgresEngine` object. The `PostgresEngine` configures a connection pool to your Cloud SQL database, enabling successful connections from your application and following industry best practices.\n", - "\n", - "To create a `PostgresEngine` using `PostgresEngine.from_instance()` you need to provide only 4 things:\n", - "\n", - "1. `project_id` : Project ID of the Google Cloud Project where the Cloud SQL instance is located.\n", - "1. `region` : Region where the Cloud SQL instance is located.\n", - "1. `instance` : The name of the Cloud SQL instance.\n", - "1. `database` : The name of the database to connect to on the Cloud SQL instance.\n", - "\n", - "By default, [IAM database authentication](https://cloud.google.com/sql/docs/postgres/iam-authentication#iam-db-auth) will be used as the method of database authentication. This library uses the IAM principal belonging to the [Application Default Credentials (ADC)](https://cloud.google.com/docs/authentication/application-default-credentials) sourced from the envionment.\n", - "\n", - "For more informatin on IAM database authentication please see:\n", - "\n", - "* [Configure an instance for IAM database authentication](https://cloud.google.com/sql/docs/postgres/create-edit-iam-instances)\n", - "* [Manage users with IAM database authentication](https://cloud.google.com/sql/docs/postgres/add-manage-iam-users)\n", - "\n", - "Optionally, [built-in database authentication](https://cloud.google.com/sql/docs/postgres/built-in-authentication) using a username and password to access the Cloud SQL database can also be used. Just provide the optional `user` and `password` arguments to `PostgresEngine.from_instance()`:\n", - "\n", - "* `user` : Database user to use for built-in database authentication and login\n", - "* `password` : Database password to use for built-in database authentication and login.\n" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "\"**Note**: This tutorial demonstrates the async interface. All async methods have corresponding sync methods.\"" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "from langchain_google_cloud_sql_pg import PostgresEngine\n", - "\n", - "engine = await PostgresEngine.afrom_instance(\n", - " project_id=PROJECT_ID, region=REGION, instance=INSTANCE, database=DATABASE\n", - ")" - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "D9Xs2qhm6X56" - }, - "source": [ - "### Initialize a table\n", - "The `PostgresVectorStore` class requires a database table. The `PostgresEngine` engine has a helper method `init_vectorstore_table()` that can be used to create a table with the proper schema for you." - ] - }, - { - "cell_type": "code", - "execution_count": 34, - "metadata": { - "id": "avlyHEMn6gzU" - }, - "outputs": [], - "source": [ - "from langchain_google_cloud_sql_pg import PostgresEngine\n", - "\n", - "await engine.ainit_vectorstore_table(\n", - " table_name=TABLE_NAME,\n", - " vector_size=768, # Vector size for VertexAI model(textembedding-gecko@latest)\n", - ")" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "### Create an embedding class instance\n", - "\n", - "You can use any [LangChain embeddings model](https://python.langchain.com/docs/integrations/text_embedding/).\n", - "You may need to enable Vertex AI API to use `VertexAIEmbeddings`. We recommend setting the embedding model's version for production, learn more about the [Text embeddings models](https://cloud.google.com/vertex-ai/docs/generative-ai/model-reference/text-embeddings)." - ] - }, - { - "cell_type": "code", - "execution_count": 3, - "id": "5utKIdq7KYi5", - "metadata": { - "id": "5utKIdq7KYi5" - }, - "outputs": [], - "source": [ - "# enable Vertex AI API\n", - "!gcloud services enable aiplatform.googleapis.com" - ] - }, - { - "cell_type": "code", - "execution_count": 16, - "metadata": { - "colab": { - "base_uri": "https://localhost:8080/" - }, - "id": "Vb2RJocV9_LQ", - "outputId": "37f5dc74-2512-47b2-c135-f34c10afdcf4" - }, - "outputs": [], - "source": [ - "from langchain_google_vertexai import VertexAIEmbeddings\n", - "\n", - "embedding = VertexAIEmbeddings(\n", - " model_name=\"textembedding-gecko@latest\", project=PROJECT_ID\n", - ")" - ] - }, - { - "cell_type": "markdown", - "metadata": { - "id": "e1tl0aNx7SWy" - }, - "source": [ - "### Initialize a default PostgresVectorStore" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": { - "id": "z-AZyzAQ7bsf" - }, - "outputs": [], - "source": [ - "from langchain_google_cloud_sql_pg import PostgresVectorStore\n", - "\n", - "store = await PostgresVectorStore.create( # Use .create() to initialize an async vector store\n", - " engine=engine,\n", - " table_name=TABLE_NAME,\n", - " embedding_service=embedding,\n", - ")" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "### Add texts" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "import uuid\n", - "\n", - "all_texts = [\"Apples and oranges\", \"Cars and airplanes\", \"Pineapple\", \"Train\", \"Banana\"]\n", - "metadatas = [{\"len\": len(t)} for t in all_texts]\n", - "ids = [str(uuid.uuid4()) for _ in all_texts]\n", - "\n", - "await store.aadd_texts(all_texts, metadatas=metadatas, ids=ids)" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "### Delete texts" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "await store.adelete([ids[1]])" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "### Search for documents" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "query = \"I'd like a fruit.\"\n", - "docs = await store.asimilarity_search(query)\n", - "print(docs)" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "### Search for documents by vector" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "query_vector = embedding.embed_query(query)\n", - "docs = await store.asimilarity_search_by_vector(query_vector, k=2)\n", - "print(docs)" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "## Add a Index\n", - "Speed up vector search queries by applying a vector index. Learn more about [vector indexes](https://cloud.google.com/blog/products/databases/faster-similarity-search-performance-with-pgvector-indexes)." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "from langchain_google_cloud_sql_pg.indexes import IVFFlatIndex\n", - "\n", - "index = IVFFlatIndex()\n", - "await store.aapply_vector_index(index)" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "### Re-index" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "await store.areindex() # Re-index using default index name" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "### Remove an index" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "await store.aadrop_vector_index() # Delete index using default name" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "## Create a custom Vector Store\n", - "A Vector Store can take advantage of relational data to filter similarity searches.\n", - "\n", - "Create a table with custom metadata columns." - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "from langchain_google_cloud_sql_pg import Column\n", - "\n", - "# Set table name\n", - "TABLE_NAME = \"vectorstore_custom\"\n", - "\n", - "await engine.ainit_vectorstore_table(\n", - " table_name=TABLE_NAME,\n", - " vector_size=768, # VertexAI model: textembedding-gecko@latest\n", - " metadata_columns=[Column(\"len\", \"INTEGER\")],\n", - ")\n", - "\n", - "\n", - "# Initialize PostgresVectorStore\n", - "custom_store = await PostgresVectorStore.create(\n", - " engine=engine,\n", - " table_name=TABLE_NAME,\n", - " embedding_service=embedding,\n", - " metadata_columns=[\"len\"],\n", - " # Connect to a existing VectorStore by customizing the table schema:\n", - " # id_column=\"uuid\",\n", - " # content_column=\"documents\",\n", - " # embedding_column=\"vectors\",\n", - ")" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "### Search for documents with metadata filter" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "import uuid\n", - "\n", - "# Add texts to the Vector Store\n", - "all_texts = [\"Apples and oranges\", \"Cars and airplanes\", \"Pineapple\", \"Train\", \"Banana\"]\n", - "metadatas = [{\"len\": len(t)} for t in all_texts]\n", - "ids = [str(uuid.uuid4()) for _ in all_texts]\n", - "await store.aadd_texts(all_texts, metadatas=metadatas, ids=ids)\n", - "\n", - "# Use filter on search\n", - "docs = await custom_store.asimilarity_search_by_vector(query_vector, filter=\"len >= 6\")\n", - "\n", - "print(docs)" - ] - } - ], - "metadata": { + "cells": [ + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "# Google Cloud SQL for PostgreSQL\n", + "\n", + "> [Cloud SQL](https://cloud.google.com/sql) is a fully managed relational database service that offers high performance, seamless integration, and impressive scalability. It offers PostgreSQL, PostgreSQL, and SQL Server database engines. Extend your database application to build AI-powered experiences leveraging Cloud SQL's Langchain integrations.\n", + "\n", + "This notebook goes over how to use `Cloud SQL for PostgreSQL` to store vector embeddings with the `PostgresVectorStore` class.\n", + "\n", + "Learn more about the package on [GitHub](https://github.com/googleapis/langchain-google-cloud-sql-pg-python/).\n", + "\n", + "[![Open In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/googleapis/langchain-google-cloud-sql-pg-python/blob/main/docs/vector_store.ipynb)" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "## Before you begin\n", + "\n", + "To run this notebook, you will need to do the following:\n", + "\n", + " * [Create a Google Cloud Project](https://developers.google.com/workspace/guides/create-project)\n", + " * [Enable the Cloud SQL Admin API.](https://console.cloud.google.com/flows/enableapi?apiid=sqladmin.googleapis.com)\n", + " * [Create a Cloud SQL instance.](https://cloud.google.com/sql/docs/postgres/connect-instance-auth-proxy#create-instance)\n", + " * [Create a Cloud SQL database.](https://cloud.google.com/sql/docs/postgres/create-manage-databases)\n", + " * [Add a User to the database.](https://cloud.google.com/sql/docs/postgres/create-manage-users)" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "IR54BmgvdHT_" + }, + "source": [ + "### 🦜🔗 Library Installation\n", + "Install the integration library, `langchain-google-cloud-sql-pg`, and the library for the embedding service, `langchain-google-vertexai`." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": { "colab": { - "provenance": [], - "toc_visible": true - }, - "kernelspec": { - "display_name": "Python 3", - "name": "python3" - }, - "language_info": { - "codemirror_mode": { - "name": "ipython", - "version": 3 - }, - "file_extension": ".py", - "mimetype": "text/x-python", - "name": "python", - "nbconvert_exporter": "python", - "pygments_lexer": "ipython3", - "version": "3.11.5" - } - }, - "nbformat": 4, - "nbformat_minor": 0 + "base_uri": "https://localhost:8080/", + "height": 1000 + }, + "id": "0ZITIDE160OD", + "outputId": "e184bc0d-6541-4e0a-82d2-1e216db00a2d" + }, + "outputs": [], + "source": [ + "%pip install --upgrade --quiet langchain-google-cloud-sql-pg langchain-google-vertexai" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "v40bB_GMcr9f" + }, + "source": [ + "**Colab only:** Uncomment the following cell to restart the kernel or use the button to restart the kernel. For Vertex AI Workbench you can restart the terminal using the button on top." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "v6jBDnYnNM08", + "metadata": { + "id": "v6jBDnYnNM08" + }, + "outputs": [], + "source": [ + "# # Automatically restart kernel after installs so that your environment can access the new packages\n", + "# import IPython\n", + "\n", + "# app = IPython.Application.instance()\n", + "# app.kernel.do_shutdown(True)" + ] + }, + { + "cell_type": "markdown", + "id": "yygMe6rPWxHS", + "metadata": { + "id": "yygMe6rPWxHS" + }, + "source": [ + "### 🔐 Authentication\n", + "Authenticate to Google Cloud as the IAM user logged into this notebook in order to access your Google Cloud Project.\n", + "\n", + "* If you are using Colab to run this notebook, use the cell below and continue.\n", + "* If you are using Vertex AI Workbench, check out the setup instructions [here](https://github.com/GoogleCloudPlatform/generative-ai/tree/main/setup-env)." + ] + }, + { + "cell_type": "code", + "execution_count": 1, + "id": "PTXN1_DSXj2b", + "metadata": { + "id": "PTXN1_DSXj2b" + }, + "outputs": [], + "source": [ + "from google.colab import auth\n", + "\n", + "auth.authenticate_user()" + ] + }, + { + "cell_type": "markdown", + "id": "NEvB9BoLEulY", + "metadata": { + "id": "NEvB9BoLEulY" + }, + "source": [ + "### ☁ Set Your Google Cloud Project\n", + "Set your Google Cloud project so that you can leverage Google Cloud resources within this notebook.\n", + "\n", + "If you don't know your project ID, try the following:\n", + "\n", + "* Run `gcloud config list`.\n", + "* Run `gcloud projects list`.\n", + "* See the support page: [Locate the project ID](https://support.google.com/googleapi/answer/7014113)." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "gfkS3yVRE4_W", + "metadata": { + "cellView": "form", + "id": "gfkS3yVRE4_W" + }, + "outputs": [], + "source": [ + "# @markdown Please fill in the value below with your Google Cloud project ID and then run the cell.\n", + "\n", + "PROJECT_ID = \"my-project-id\" # @param {type:\"string\"}\n", + "\n", + "# Set the project id\n", + "!gcloud config set project {PROJECT_ID}" + ] + }, + { + "cell_type": "markdown", + "id": "f8f2830ee9ca1e01", + "metadata": { + "id": "f8f2830ee9ca1e01" + }, + "source": [ + "## Basic Usage" + ] + }, + { + "cell_type": "markdown", + "id": "OMvzMWRrR6n7", + "metadata": { + "id": "OMvzMWRrR6n7" + }, + "source": [ + "### Set Cloud SQL database values\n", + "Find your database values, in the [Cloud SQL Instances page](https://console.cloud.google.com/sql?_ga=2.223735448.2062268965.1707700487-2088871159.1707257687)." + ] + }, + { + "cell_type": "code", + "execution_count": 4, + "id": "irl7eMFnSPZr", + "metadata": { + "id": "irl7eMFnSPZr" + }, + "outputs": [], + "source": [ + "# @title Set Your Values Here { display-mode: \"form\" }\n", + "REGION = \"us-central1\" # @param {type: \"string\"}\n", + "INSTANCE = \"my-pg-instance\" # @param {type: \"string\"}\n", + "DATABASE = \"my-database\" # @param {type: \"string\"}\n", + "TABLE_NAME = \"vector_store\" # @param {type: \"string\"}" + ] + }, + { + "cell_type": "markdown", + "id": "QuQigs4UoFQ2", + "metadata": { + "id": "QuQigs4UoFQ2" + }, + "source": [ + "### PostgresEngine Connection Pool\n", + "\n", + "One of the requirements and arguments to establish Cloud SQL as a vector store is a `PostgresEngine` object. The `PostgresEngine` configures a connection pool to your Cloud SQL database, enabling successful connections from your application and following industry best practices.\n", + "\n", + "To create a `PostgresEngine` using `PostgresEngine.from_instance()` you need to provide only 4 things:\n", + "\n", + "1. `project_id` : Project ID of the Google Cloud Project where the Cloud SQL instance is located.\n", + "1. `region` : Region where the Cloud SQL instance is located.\n", + "1. `instance` : The name of the Cloud SQL instance.\n", + "1. `database` : The name of the database to connect to on the Cloud SQL instance.\n", + "\n", + "By default, [IAM database authentication](https://cloud.google.com/sql/docs/postgres/iam-authentication#iam-db-auth) will be used as the method of database authentication. This library uses the IAM principal belonging to the [Application Default Credentials (ADC)](https://cloud.google.com/docs/authentication/application-default-credentials) sourced from the envionment.\n", + "\n", + "For more informatin on IAM database authentication please see:\n", + "\n", + "* [Configure an instance for IAM database authentication](https://cloud.google.com/sql/docs/postgres/create-edit-iam-instances)\n", + "* [Manage users with IAM database authentication](https://cloud.google.com/sql/docs/postgres/add-manage-iam-users)\n", + "\n", + "Optionally, [built-in database authentication](https://cloud.google.com/sql/docs/postgres/built-in-authentication) using a username and password to access the Cloud SQL database can also be used. Just provide the optional `user` and `password` arguments to `PostgresEngine.from_instance()`:\n", + "\n", + "* `user` : Database user to use for built-in database authentication and login\n", + "* `password` : Database password to use for built-in database authentication and login.\n" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "\"**Note**: This tutorial demonstrates the async interface. All async methods have corresponding sync methods.\"" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "from langchain_google_cloud_sql_pg import PostgresEngine\n", + "\n", + "engine = await PostgresEngine.afrom_instance(\n", + " project_id=PROJECT_ID, region=REGION, instance=INSTANCE, database=DATABASE\n", + ")" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "D9Xs2qhm6X56" + }, + "source": [ + "### Initialize a table\n", + "The `PostgresVectorStore` class requires a database table. The `PostgresEngine` engine has a helper method `init_vectorstore_table()` that can be used to create a table with the proper schema for you." + ] + }, + { + "cell_type": "code", + "execution_count": 34, + "metadata": { + "id": "avlyHEMn6gzU" + }, + "outputs": [], + "source": [ + "from langchain_google_cloud_sql_pg import PostgresEngine\n", + "\n", + "await engine.ainit_vectorstore_table(\n", + " table_name=TABLE_NAME,\n", + " vector_size=768, # Vector size for VertexAI model(textembedding-gecko@latest)\n", + ")" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "### Create an embedding class instance\n", + "\n", + "You can use any [LangChain embeddings model](https://python.langchain.com/docs/integrations/text_embedding/).\n", + "You may need to enable Vertex AI API to use `VertexAIEmbeddings`. We recommend setting the embedding model's version for production, learn more about the [Text embeddings models](https://cloud.google.com/vertex-ai/docs/generative-ai/model-reference/text-embeddings)." + ] + }, + { + "cell_type": "code", + "execution_count": 3, + "id": "5utKIdq7KYi5", + "metadata": { + "id": "5utKIdq7KYi5" + }, + "outputs": [], + "source": [ + "# enable Vertex AI API\n", + "!gcloud services enable aiplatform.googleapis.com" + ] + }, + { + "cell_type": "code", + "execution_count": 16, + "metadata": { + "colab": { + "base_uri": "https://localhost:8080/" + }, + "id": "Vb2RJocV9_LQ", + "outputId": "37f5dc74-2512-47b2-c135-f34c10afdcf4" + }, + "outputs": [], + "source": [ + "from langchain_google_vertexai import VertexAIEmbeddings\n", + "\n", + "embedding = VertexAIEmbeddings(\n", + " model_name=\"textembedding-gecko@latest\", project=PROJECT_ID\n", + ")" + ] + }, + { + "cell_type": "markdown", + "metadata": { + "id": "e1tl0aNx7SWy" + }, + "source": [ + "### Initialize a default PostgresVectorStore" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": { + "id": "z-AZyzAQ7bsf" + }, + "outputs": [], + "source": [ + "from langchain_google_cloud_sql_pg import PostgresVectorStore\n", + "\n", + "store = await PostgresVectorStore.create( # Use .create() to initialize an async vector store\n", + " engine=engine,\n", + " table_name=TABLE_NAME,\n", + " embedding_service=embedding,\n", + ")" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "### Add texts" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "import uuid\n", + "\n", + "all_texts = [\"Apples and oranges\", \"Cars and airplanes\", \"Pineapple\", \"Train\", \"Banana\"]\n", + "metadatas = [{\"len\": len(t)} for t in all_texts]\n", + "ids = [str(uuid.uuid4()) for _ in all_texts]\n", + "\n", + "await store.aadd_texts(all_texts, metadatas=metadatas, ids=ids)" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "### Delete texts" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "await store.adelete([ids[1]])" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "### Search for documents" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "query = \"I'd like a fruit.\"\n", + "docs = await store.asimilarity_search(query)\n", + "print(docs)" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "### Search for documents by vector" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "query_vector = embedding.embed_query(query)\n", + "docs = await store.asimilarity_search_by_vector(query_vector, k=2)\n", + "print(docs)" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "## Add a Index\n", + "Speed up vector search queries by applying a vector index. Learn more about [vector indexes](https://cloud.google.com/blog/products/databases/faster-similarity-search-performance-with-pgvector-indexes)." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "from langchain_google_cloud_sql_pg.indexes import IVFFlatIndex\n", + "\n", + "index = IVFFlatIndex()\n", + "await store.aapply_vector_index(index)" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "### Re-index" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "await store.areindex() # Re-index using default index name" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "### Remove an index" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "await store.aadrop_vector_index() # Delete index using default name" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "## Create a custom Vector Store\n", + "A Vector Store can take advantage of relational data to filter similarity searches.\n", + "\n", + "Create a table with custom metadata columns." + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "from langchain_google_cloud_sql_pg import Column\n", + "\n", + "# Set table name\n", + "TABLE_NAME = \"vectorstore_custom\"\n", + "\n", + "await engine.ainit_vectorstore_table(\n", + " table_name=TABLE_NAME,\n", + " vector_size=768, # VertexAI model: textembedding-gecko@latest\n", + " metadata_columns=[Column(\"len\", \"INTEGER\")],\n", + ")\n", + "\n", + "\n", + "# Initialize PostgresVectorStore\n", + "custom_store = await PostgresVectorStore.create(\n", + " engine=engine,\n", + " table_name=TABLE_NAME,\n", + " embedding_service=embedding,\n", + " metadata_columns=[\"len\"],\n", + " # Connect to a existing VectorStore by customizing the table schema:\n", + " # id_column=\"uuid\",\n", + " # content_column=\"documents\",\n", + " # embedding_column=\"vectors\",\n", + ")" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "### Search for documents with metadata filter" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "import uuid\n", + "\n", + "# Add texts to the Vector Store\n", + "all_texts = [\"Apples and oranges\", \"Cars and airplanes\", \"Pineapple\", \"Train\", \"Banana\"]\n", + "metadatas = [{\"len\": len(t)} for t in all_texts]\n", + "ids = [str(uuid.uuid4()) for _ in all_texts]\n", + "await store.aadd_texts(all_texts, metadatas=metadatas, ids=ids)\n", + "\n", + "# Use filter on search\n", + "docs = await custom_store.asimilarity_search_by_vector(query_vector, filter=\"len >= 6\")\n", + "\n", + "print(docs)" + ] + } + ], + "metadata": { + "colab": { + "provenance": [], + "toc_visible": true + }, + "kernelspec": { + "display_name": "Python 3", + "name": "python3" + }, + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.11.5" + } + }, + "nbformat": 4, + "nbformat_minor": 0 } \ No newline at end of file diff --git a/integration.cloudbuild.yaml b/integration.cloudbuild.yaml index 029b4e50..ed4d2a27 100644 --- a/integration.cloudbuild.yaml +++ b/integration.cloudbuild.yaml @@ -14,17 +14,21 @@ steps: - id: Install dependencies - name: python:3.11 - entrypoint: pip - args: ["install", "--user", "-r", "requirements.txt"] + name: python:${_VERSION} + entrypoint: /bin/bash + args: + - -c + - | + if [[ $_VERSION == "3.8" ]]; then version="-3.8"; fi + pip install --user -r requirements${version}.txt - id: Install module (and test requirements) - name: python:3.11 + name: python:${_VERSION} entrypoint: pip args: ["install", ".[test]", "--user"] - id: Run integration tests - name: python:3.11 + name: python:${_VERSION} entrypoint: python args: ["-m", "pytest"] env: @@ -44,3 +48,7 @@ availableSecrets: substitutions: _DATABASE_ID: test-database _REGION: us-central1 + _VERSION: "3.8" + +options: + dynamicSubstitutions: true diff --git a/pyproject.toml b/pyproject.toml index a7ca551f..1ab88ddb 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -12,7 +12,7 @@ dependencies = [ "cloud-sql-python-connector[asyncpg] >= 1.7.0, <2.0.0", "langchain-core>=0.1.1, <2.0.0 ", "langchain-community>=0.0.18, <0.1.0", - "numpy>=1.26.4, <2.0.0", + "numpy>=1.24.4, <2.0.0", "pgvector>=0.2.5, <1.0.0", "SQLAlchemy>=2.0.25, <3.0.0" ] @@ -28,10 +28,10 @@ Changelog = "https://github.com/googleapis/langchain-google-cloud-sql-pg-python/%20%20[project.optional-dependencies]%20test%20=%20[-"black[jupyter]==23.12.0", + "black[jupyter]==23.12.1", "isort==5.13.2", - "mypy==1.7.1", - "pytest-asyncio==0.23.0", + "mypy==1.9.0", + "pytest-asyncio==0.23.5.post1", "pytest==7.4.4" ] diff --git a/requirements-3.8.txt b/requirements-3.8.txt new file mode 100644 index 00000000..779f7e44 --- /dev/null +++ b/requirements-3.8.txt @@ -0,0 +1,6 @@ +cloud-sql-python-connector[asyncpg]==1.8.0 +langchain-core==0.1.32 +langchain-community==0.0.28 +numpy==1.24.4 +pgvector==0.2.5 +SQLAlchemy==2.0.28 diff --git a/requirements.txt b/requirements.txt index d53ef538..42eaaded 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,6 +1,6 @@ -cloud-sql-python-connector[asyncpg]==1.7.0 -langchain-core==0.1.23 -langchain-community==0.0.18 +cloud-sql-python-connector[asyncpg]==1.8.0 +langchain-core==0.1.32 +langchain-community==0.0.28 numpy==1.26.4 pgvector==0.2.5 -SQLAlchemy==2.0.27 +SQLAlchemy==2.0.28 diff --git a/samples/langchain_quick_start.ipynb b/samples/langchain_quick_start.ipynb index a246932c..06440a48 100644 --- a/samples/langchain_quick_start.ipynb +++ b/samples/langchain_quick_start.ipynb @@ -34,7 +34,7 @@ "---\n", "# **Introduction**\n", "\n", - "In this codelab you will learn how to create an interactive generative AI application with Retrieval Augmented Generation using [Cloud SQL for PostgreSQL](https://cloud.google.com/sql/docs/postgres) and [LangChain](https://www.langchain.com/). We will be creating an application grounded in a [Netflix Movie dataset](https://www.kaggle.com/datasets/shivamb/netflix-shows)." + "In this codelab, you'll learn how to create a powerful interactive generative AI application using Retrieval Augmented Generation powered by [Cloud SQL for PostgreSQL](https://cloud.google.com/sql/docs/postgres) and [LangChain](https://www.langchain.com/). We will be creating an application grounded in a [Netflix Movie dataset](https://www.kaggle.com/datasets/shivamb/netflix-shows), allowing you to interact with movie data in exciting new ways." ] }, { @@ -108,8 +108,7 @@ }, "outputs": [], "source": [ - "# TODO: Update this to install from Pypi\n", - "%pip install --upgrade --quiet git+https://github.com/googleapis/langchain-google-cloud-sql-pg-python.git langchain-google-vertexai" + "%pip install --upgrade --quiet langchain-google-cloud-sql-pg langchain-google-vertexai langchain" ] }, { @@ -169,8 +168,8 @@ "cell_type": "code", "execution_count": null, "metadata": { - "id": "qjFuhRhVxlWP", - "cellView": "form" + "cellView": "form", + "id": "qjFuhRhVxlWP" }, "outputs": [], "source": [ @@ -263,8 +262,8 @@ "cell_type": "code", "execution_count": null, "metadata": { - "id": "XXI1uUu3y8gc", - "cellView": "form" + "cellView": "form", + "id": "XXI1uUu3y8gc" }, "outputs": [], "source": [ @@ -290,7 +289,12 @@ " !gcloud sql instances create {instance_name} --database-version=POSTGRES_15 \\\n", " --region={region} --cpu=1 --memory=4GB --root-password={password} \\\n", " --database-flags=cloudsql.iam_authentication=On\n", - " !gcloud sql databases create {database_name} --instance={instance_name}\n" + " !gcloud sql databases create {database_name} --instance={instance_name}\n", + "\n", + "\n", + "databases = !gcloud sql databases list --instance={instance_name} --format=\"value(name)\"\n", + "if database_name not in databases:\n", + " !gcloud sql databases create {database_name} --instance={instance_name}" ] }, { @@ -337,7 +341,7 @@ "outputs": [], "source": [ "# Import the Netflix titles table using gcloud command\n", - "import_command_output = !gcloud sql import sql {instance_name} gs://cloud-samples-data/langchain/postgres/langchain_postgres_netflix_titles.sql --database={database_name} --quiet\n", + "import_command_output = !gcloud sql import sql {instance_name} gs://cloud-samples-data/langchain/cloud-sql/postgres/first_five_netflix_titles.sql --database={database_name} --quiet\n", "\n", "if \"Imported data\" in str(import_command_output):\n", " print(import_command_output)\n", @@ -413,31 +417,6 @@ ")" ] }, - { - "cell_type": "markdown", - "metadata": { - "id": "xvCEAp97fXRt" - }, - "source": [ - "Next let's define a function \"collect_async_items\" to asynchronously pull documents from our database." - ] - }, - { - "cell_type": "code", - "execution_count": 16, - "metadata": { - "id": "-p9UiHFbdyYa" - }, - "outputs": [], - "source": [ - "async def collect_async_items(docs_generator):\n", - " \"\"\"Collects items from an async generator.\"\"\"\n", - " docs = []\n", - " async for doc in docs_generator:\n", - " docs.append(doc)\n", - " return docs" - ] - }, { "cell_type": "markdown", "metadata": { @@ -472,7 +451,7 @@ } ], "source": [ - "documents = await collect_async_items(loader.alazy_load())\n", + "documents = await loader.aload()\n", "print(f\"Loaded {len(documents)} from the database. 5 Examples:\")\n", "for doc in documents[:5]:\n", " print(doc)" @@ -565,22 +544,13 @@ "outputs": [], "source": [ "from langchain_google_vertexai import VertexAIEmbeddings\n", - "from langchain_google_cloud_sql_pg import PostgresVectorStore, PostgresEngine\n", + "from langchain_google_cloud_sql_pg import PostgresVectorStore\n", "\n", "# Initialize the embedding service. In this case we are using version 003 of Vertex AI's textembedding-gecko model. In general, it is good practice to specify the model version used.\n", "embeddings_service = VertexAIEmbeddings(\n", " model_name=\"textembedding-gecko@003\", project=project_id\n", ")\n", "\n", - "pg_engine = PostgresEngine.from_instance(\n", - " project_id=project_id,\n", - " instance=instance_name,\n", - " region=region,\n", - " database=database_name,\n", - " user=\"postgres\",\n", - " password=password,\n", - ")\n", - "\n", "vector_store = PostgresVectorStore.create_sync(\n", " engine=pg_engine,\n", " embedding_service=embeddings_service,\n", @@ -647,7 +617,7 @@ "outputs": [], "source": [ "# Import the netflix titles with vector table using gcloud command\n", - "import_command_output = !gcloud sql import sql {instance_name} gs://cloud-samples-data/langchain/postgres/netflix_titles_vector_table.sql --database={database_name} --quiet\n", + "import_command_output = !gcloud sql import sql {instance_name} gs://cloud-samples-data/langchain/cloud-sql/postgres/netflix_titles_vector_table.sql --database={database_name} --quiet\n", "\n", "if \"Imported data\" in str(import_command_output):\n", " print(import_command_output)\n", @@ -685,20 +655,11 @@ "source": [ "from langchain_google_cloud_sql_pg import PostgresChatMessageHistory, PostgresEngine\n", "\n", - "pg_engine = PostgresEngine.from_instance(\n", - " project_id=project_id,\n", - " instance=instance_name,\n", - " region=region,\n", - " database=database_name,\n", - " user=\"postgres\",\n", - " password=password,\n", - ")\n", - "\n", "message_table_name = \"message_store\"\n", "\n", "pg_engine.init_chat_history_table(table_name=message_table_name)\n", "\n", - "chat_history = PostgresChatMessageHistory(\n", + "chat_history = PostgresChatMessageHistory.create_sync(\n", " pg_engine,\n", " session_id=\"my-test-session\",\n", " table_name=message_table_name,\n", @@ -790,12 +751,12 @@ " PostgresChatMessageHistory,\n", ")\n", "\n", - "# Intialize the embedding service\n", + "# Initialize the embedding service\n", "embeddings_service = VertexAIEmbeddings(\n", " model_name=\"textembedding-gecko@latest\", project=project_id\n", ")\n", "\n", - "# Intialize the engine\n", + "# Initialize the engine\n", "pg_engine = PostgresEngine.from_instance(\n", " project_id=project_id,\n", " instance=instance_name,\n", @@ -805,7 +766,7 @@ " password=password,\n", ")\n", "\n", - "# Intialize the Vector Store\n", + "# Initialize the Vector Store\n", "vector_table_name = \"movie_vector_table\"\n", "vector_store = PostgresVectorStore.create_sync(\n", " engine=pg_engine,\n", @@ -822,8 +783,8 @@ " ],\n", ")\n", "\n", - "# Intialize the PostgresChatMessageHistory\n", - "chat_history = PostgresChatMessageHistory(\n", + "# Initialize the PostgresChatMessageHistory\n", + "chat_history = PostgresChatMessageHistory.create_sync(\n", " pg_engine,\n", " session_id=\"my-test-session\",\n", " table_name=\"message_store\",\n", @@ -892,7 +853,7 @@ }, "outputs": [], "source": [ - "# Intialize retriever, llm and memory for the chain\n", + "# Initialize retriever, llm and memory for the chain\n", "retriever = vector_store.as_retriever(\n", " search_type=\"mmr\", search_kwargs={\"k\": 5, \"lambda_mult\": 0.8}\n", ")" @@ -904,7 +865,7 @@ "id": "3maZ8SLlneYJ" }, "source": [ - "Now let's intialize our LLM, in this case we are using Vertex AI's \"gemini-pro\"." + "Now let's initialize our LLM, in this case we are using Vertex AI's \"gemini-pro\"." ] }, { @@ -1041,9 +1002,18 @@ "name": "python3" }, "language_info": { - "name": "python" + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.11.5" } }, "nbformat": 4, "nbformat_minor": 0 -} \ No newline at end of file +} diff --git a/src/langchain_google_cloud_sql_pg/__init__.py b/src/langchain_google_cloud_sql_pg/__init__.py index 0c607c16..f0d2eab0 100644 --- a/src/langchain_google_cloud_sql_pg/__init__.py +++ b/src/langchain_google_cloud_sql_pg/__init__.py @@ -15,7 +15,7 @@ from . import indexes from .chat_message_history import PostgresChatMessageHistory from .engine import Column, PostgresEngine -from .postgresql_loader import PostgresDocumentSaver, PostgresLoader +from .loader import PostgresDocumentSaver, PostgresLoader from .vectorstore import PostgresVectorStore from .version import __version__ diff --git a/src/langchain_google_cloud_sql_pg/engine.py b/src/langchain_google_cloud_sql_pg/engine.py index 632b0659..97af397b 100644 --- a/src/langchain_google_cloud_sql_pg/engine.py +++ b/src/langchain_google_cloud_sql_pg/engine.py @@ -259,9 +259,8 @@ async def ainit_vectorstore_table( "{content_column}" TEXT NOT NULL, "{embedding_column}" vector({vector_size}) NOT NULL""" for column in metadata_columns: - query += f""",\n"{column.name}" {column.data_type}""" + ( - "NOT NULL" if not column.nullable else "" - ) + nullable = "NOT NULL" if not column.nullable else "" + query += f',\n"{column.name}" {column.data_type} {nullable}' if store_metadata: query += f""",\n"{metadata_json_column}" JSON""" query += "\n);" @@ -333,9 +332,8 @@ async def ainit_document_table( {content_column} TEXT NOT NULL """ for column in metadata_columns: - query += f',\n"{column.name}" {column.data_type}' + ( - "NOT NULL" if not column.nullable else "" - ) + nullable = "NOT NULL" if not column.nullable else "" + query += f',\n"{column.name}" {column.data_type} {nullable}' metadata_json_column = metadata_json_column or "langchain_metadata" if store_metadata: query += f',\n"{metadata_json_column}" JSON' diff --git a/src/langchain_google_cloud_sql_pg/postgresql_loader.py b/src/langchain_google_cloud_sql_pg/loader.py similarity index 100% rename from src/langchain_google_cloud_sql_pg/postgresql_loader.py rename to src/langchain_google_cloud_sql_pg/loader.py diff --git a/src/langchain_google_cloud_sql_pg/vectorstore.py b/src/langchain_google_cloud_sql_pg/vectorstore.py index 1476347d..b06343b6 100644 --- a/src/langchain_google_cloud_sql_pg/vectorstore.py +++ b/src/langchain_google_cloud_sql_pg/vectorstore.py @@ -93,7 +93,7 @@ async def create( lambda_mult: float = 0.5, index_query_options: Optional[QueryOptions] = None, ): - """Constructor for CloudSQLVectorStore. + """Constructor for PostgresVectorStore. Args: engine (PostgresEngine): AsyncEngine with pool connection to the postgres database. Required. embedding_service (Embeddings): Text embedding model to use. diff --git a/src/langchain_google_cloud_sql_pg/version.py b/src/langchain_google_cloud_sql_pg/version.py index f109efad..fd9ab04f 100644 --- a/src/langchain_google_cloud_sql_pg/version.py +++ b/src/langchain_google_cloud_sql_pg/version.py @@ -13,4 +13,4 @@ # See the License for the specific language governing permissions and # limitations under the License. # -__version__ = "0.1.0" +__version__ = "0.2.0" diff --git a/tests/test_cloudsql_vectorstore.py b/tests/test_cloudsql_vectorstore.py index a296b526..675b381f 100644 --- a/tests/test_cloudsql_vectorstore.py +++ b/tests/test_cloudsql_vectorstore.py @@ -35,7 +35,7 @@ Document(page_content=texts[i], metadata=metadatas[i]) for i in range(len(texts)) ] -embeddings = [embeddings_service.embed_query("foo") for i in range(len(texts))] +embeddings = [embeddings_service.embed_query(texts[i]) for i in range(len(texts))] def get_env_var(key: str, desc: str) -> str: @@ -61,7 +61,7 @@ def db_instance(self) -> str: @pytest.fixture(scope="module") def db_name(self) -> str: - return get_env_var("DATABASE_ID", "instance for cloud sql") + return get_env_var("DATABASE_ID", "database name on cloud sql instance") @pytest_asyncio.fixture(scope="class") async def engine(self, db_project, db_region, db_instance, db_name): diff --git a/tests/test_cloudsql_vectorstore_from_methods.py b/tests/test_cloudsql_vectorstore_from_methods.py index ee96d4db..e0439c97 100644 --- a/tests/test_cloudsql_vectorstore_from_methods.py +++ b/tests/test_cloudsql_vectorstore_from_methods.py @@ -36,7 +36,7 @@ Document(page_content=texts[i], metadata=metadatas[i]) for i in range(len(texts)) ] -embeddings = [embeddings_service.embed_query("foo") for i in range(len(texts))] +embeddings = [embeddings_service.embed_query(texts[i]) for i in range(len(texts))] def get_env_var(key: str, desc: str) -> str: @@ -62,7 +62,7 @@ def db_instance(self) -> str: @pytest.fixture(scope="module") def db_name(self) -> str: - return get_env_var("DATABASE_ID", "instance for cloud sql") + return get_env_var("DATABASE_ID", "database name on cloud sql instance") @pytest_asyncio.fixture async def engine(self, db_project, db_region, db_instance, db_name): @@ -176,8 +176,6 @@ async def test_afrom_texts_custom(self, engine): assert results[0]["page"] is None assert results[0]["source"] is None - ids = [str(uuid.uuid4()) for i in range(len(texts))] - async def test_afrom_docs_custom(self, engine): ids = [str(uuid.uuid4()) for i in range(len(texts))] docs = [ diff --git a/tests/test_cloudsql_vectorstore_index.py b/tests/test_cloudsql_vectorstore_index.py index d770c2c7..bb70b6d7 100644 --- a/tests/test_cloudsql_vectorstore_index.py +++ b/tests/test_cloudsql_vectorstore_index.py @@ -14,6 +14,7 @@ import os +import sys import uuid import pytest @@ -53,6 +54,10 @@ def get_env_var(key: str, desc: str) -> str: @pytest.mark.asyncio(scope="class") +@pytest.mark.skipif( + sys.version_info != (3, 11), + reason="To prevent index clashes only run on python3.11 or higher", +) class TestIndex: @pytest.fixture(scope="module") def db_project(self) -> str: