Repository navigation
Add CI that tests each Snowflake sample on Snowflake Next - #22
Merged
Merged
Conversation
Run every sample against the LocalStack Snowflake emulator in a GitHub Actions matrix, each with a test.sh behind `make test`, and fix the setup steps that no longer work. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
HarshCasper
requested review from
hovaesco,
sabir-akhadov-localstack and
whummer
as code owners
October 13, 2026 13:48
- soda: match Soda's check output and use a schema check that works without Soda Cloud - citi-bike: seed into test.public, where the app reads from - fraud detection: run scripts through a make macro instead of goal arguments - customer spend: Snowflake-style column names and a numeric-only correlation - streamlit: replace the PostgreSQL BIT cast in setup.sql - airflow: pin Airflow 2.10.3, the DAG uses Airflow 2 APIs - multi-container: read the logs straight from both containers Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
- soda: Snowflake stores unquoted column names in upper case - streamlit: run on bullseye, the pinned oscrypto cannot read OpenSSL 3 - citi-bike: pass the account and schema to the Node.js connection - multi-container: IPv4 health checks and health details in the logs - airflow, customer spend: diagnostics for the open failures Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
- citi-bike: date_trunc takes 'day' as a string, not a quoted identifier - customer spend: write to the public schema, test.test does not exist - streamlit: report the emulator's SAMPLE-on-subquery failure and check the preview with LIMIT - airflow: relative DAG path and the requirements file, as MWAA expects - multi-container: the AWS image has no curl, use Python for the checks - READMEs: start LocalStack with lstk, SF_HOSTNAMES instead of SF_HOSTNAME_REGEX Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
… samples - airflow: Airflow 3 compatible DAG (connection from AIRFLOW_CONN_SNOWFLAKE_LOCAL, schedule, one task at a time, query transform.PREPPED_DATA), upload the macros folder, requirements before the environment, restart Airflow after the sync - citi-bike: group temperatures with round(x / 10) * 10, the emulator rejects round(x, -1) - streamlit: pin pyarrow 8.0.0, the version snowflake-connector-python 2.7.11 needs Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
The models config sat under my_project, but the project is named test_dbt, so dbt ignored it and built every view in PUBLIC instead of TRANSFORM and ANALYSIS. Also print the query task's log when the DAG run fails. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
hovaesco
reviewed
Oct 14, 2026
hovaesco
left a comment
Contributor
There was a problem hiding this comment.
All sample apps should be updated to use the new Snowflake Next emulator https://linear.app/localstack/issue/LAV-2294/update-sample-apps-to-use-next-emulator
Contributor
|
Plus we won't address regressions reported against Snowflake Python emualtor. |
Start localstack/snowflake-next with lstk, create the test database before seeding (a fresh Next instance has none), drop SF_CSV_IMPORT_MAX_ROWS and SF_LOG=trace, and restore round(temp_avg_f, -1), which Next supports. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
Start localstack/snowflake-next through lstk --image. A fresh Next instance only has the SNOWFLAKE database, so the customer spend notebook now creates its database before writing to it. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
Start localstack/snowflake-next through lstk --image. Soda's init now creates the test database, since Next starts with only SNOWFLAKE. Next supports SAMPLE on a subquery, so the streamlit smoke test checks the app's .sample(n=5) preview directly again. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
Switch the Snowflake service to localstack/snowflake-next. The image has no python3, so the health check uses bash /dev/tcp. SF_HOSTNAMES now replaces the built-in host list, so the default hostname comes first. The old POST /session probe returns 401 on Next, so the reachability check logs in by container name instead. SF_S3_ENDPOINT_EXTERNAL is dropped: internal stages are served by the emulator itself. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
A new session on the Next emulator has no current database, as in Snowflake, so CREATE TABLE failed with error 090105. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
snowflake-next is Snowflake only, so docker compose starts LocalStack for AWS next to it. The Lambda container joins the compose network and reaches the emulator by its service name over http, and init.sf.sql creates the database and schema the function connects to, since snowflake-next starts with only the SNOWFLAKE database. make test also reads the rows back from the emulator on host port 4567. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
LocalStack for AWS (MWAA, S3) and snowflake-next run as two Compose containers on a shared network. MAIN_DOCKER_NETWORK puts the MWAA Airflow container on that network, so the DAG and dbt reach the emulator at http://snowflake:4566. init.sf.sql creates the test database at startup. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
Start localstack/snowflake-next with lstk and run the Snowpark scripts written for Snowflake Cloud against it, which replaces the emulator workarounds and the data checkpoints they needed. The bundled data is now a scaled-down simulation from the fraud detection handbook, so feature engineering has several months of transactions to work with, and make test checks the features table as well as the loaded tables. The image moves to Python 3.11, since Snowflake no longer runs Python 3.8 UDFs, and the training script pins the UDF packages to the local versions. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
Glue and S3 run in LocalStack AWS and Snowflake in snowflake-next, as two compose containers on one network. The Glue job now reads src_glue, keeps the active rows and writes them to tgt_glue, and the test checks the rows. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
The localstack-pro image has no curl, so check health with python3. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
The Spark connector writes through the internal stage at stages.s3.localhost.localstack.cloud. LocalStack's DNS answered that name with its own S3, so resolve it upstream with Docker's DNS, where it is an alias of the Snowflake emulator. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
LocalStack fetches the Glue script through s3.localhost.localstack.cloud, so only stages.s3.localhost.localstack.cloud may go to the emulator. Print the job error and the LocalStack log tail when the job fails. Claude-Session: https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM
Member
Author
|
@hovaesco thanks, all 10 samples now run on
|
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
The repo had no CI. This adds a workflow that runs all 10 samples in a matrix against the Snowflake Next emulator (
localstack/snowflake-next), as requested in review and tracked in LAV-2294. Each sample gets atest.shbehindmake test, plusmake installand a start target.How the samples start
lstk start --type snowflake --image localstack/snowflake-next:latest(lstk 1.3.0+).docker-compose.ymlwith LocalStack AWS on 4566 and Snowflake Next on a second port, on a shared network.SF_HOSTNAMESlists that service name.SNOWFLAKEdatabase, as a new Snowflake account does. Each sample creates its database (init script or setup step) instead of relying on the old emulator creating it on connect.What each test checks
transform.PREPPED_DATAhas 14 rows./and all three chart endpoints return data.src_glueand writes the 3 active rows totgt_glue, which the test reads back.sample(n=5)preview against Snowflake, checking the result against the same filter in SQL.Sample fixes
dbt_project.ymlconfigured models undermy_project, but the project istest_dbt, so its schemas were never applied.snowflake:4566over http.test.public, and the Node connection passes the account and schema.date_trunc('day', ...)instead of a quoted identifier.snowflake:4566.PUTs reach Next while the Glue script download still goes to LocalStack S3.deploy.shfails when the job fails.handler.py, and the libraries are now built for the function's runtime./dev/tcp, because the Next image has no curl or python.SF_S3_ENDPOINT_EXTERNALis gone: Next serves internal stages itself.test.test, which does not exist. It now createstestand usestest.public.corr(numeric_only=True)for pandas 2.snowflake-cli-labswas renamed tosnowflake-cli.setup.sqlused a PostgreSQL::bit(32)cast.pyarrowis pinned to 8.0.0, the version snowflake-connector-python 2.7.11 requires.lstk --imageor Docker Compose) andmake test. The top-level README explains the two setups.Emulator bugs
Found on Next while porting, and filed:
save_as_tablefrom a stage. The fraud sample loads withcopy_into_table.SUM() / nis described as NUMBER(38,0), so Snowparksave_as_tablesilently truncates the values.ORDER BYon another column is rejected (002024). Snowpark 1.55 generates this by default. Needs a check against real Snowflake.add_packageswith pinned versions fails on a fresh emulator, so the fraud sample's model UDF can't be deployed.The earlier bugs from the Python emulator don't apply on Next:
SAMPLEon a subquery (LAV-4420) works on Next.ROUNDscale (LAV-4421) works on Next.https://claude.ai/code/session_01DZfDmzUBPqNAu3yFKyfCNM