Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: add schema updates with no key properties #52

Draft
wants to merge 2 commits into
base: main
Choose a base branch
from

Conversation

pnadolny13
Copy link
Contributor

As part of #51 I wanted to add a test to assert schema changes when reserved words were used and no key properties were present so the COPY logic would get invoked. It failed and I realized that it would have been failing before my changes in that PR.

This PR adds the test case so we can figure out how to fix it. The problem I saw was that the file in the internal stage matched the initial schema record but by the time it was being loaded into the table the second schema message had already altered the table to the new schema. Ultimately leading to an error related to a mismatch in columns in the table vs stage file columns.

pnadolny13 added a commit that referenced this pull request Jun 14, 2023
Closes #48

Sqlalchemy handles some of the quoting for reserved words but we also
build sql manually so those dont get handled. Also when doing column
diffing like to decided whether a column exists or not we need to use
uppercase column names because we created them as uppercase with quotes
so case matters.

I found a bug with the COPY logic when the stream has schema updates.
Logged it in #53
and draft PR in #52.
Once that is fixed we can add a schema change to the test records with
no key properties so we assert alters work with reserved words when no
key properties are being used.
@kgpayne
Copy link
Collaborator

kgpayne commented Jun 27, 2023

@pnadolny13 this is interesting. Sounds to me like a bug with the flushing mechanism - we should be flushing the old stream completely before creating a new stream (including stage etc.) on the arrival of a new Schema 🤔

@visch
Copy link
Member

visch commented Sep 12, 2023

Hitting something pretty similar to this but slightly different. I ran with this exactly singer data and wanted to record the current stack trace just to help someone else out if they are getting the same thing

Traceback (most recent call last):
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/sqlalchemy/engine/base.py", line 1910, in _execute_context
    self.dialect.do_execute(
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/sqlalchemy/engine/default.py", line 736, in do_execute
    cursor.execute(statement, parameters)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/snowflake/connector/cursor.py", line 908, in execute
    Error.errorhandler_wrapper(self.connection, self, error_class, errvalue)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/snowflake/connector/errors.py", line 290, in errorhandler_wrapper
    handed_over = Error.hand_to_other_handler(
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/snowflake/connector/errors.py", line 345, in hand_to_other_handler
    cursor.errorhandler(connection, cursor, error_class, error_value)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/snowflake/connector/errors.py", line 221, in default_errorhandler
    raise error_class(
snowflake.connector.errors.ProgrammingError: 002020 (21S01): 01aeedc2-0001-56f2-0004-428e0003794e: SQL compilation error:
Insert value list does not match column list expecting 13 but got 9

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/bin/target-snowflake", line 8, in <module>
    sys.exit(TargetSnowflake.cli())
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/click/core.py", line 1157, in __call__
    return self.main(*args, **kwargs)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/click/core.py", line 1078, in main
    rv = self.invoke(ctx)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/click/core.py", line 1434, in invoke
    return ctx.invoke(self.callback, **ctx.params)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/click/core.py", line 783, in invoke
    return __callback(*args, **kwargs)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/singer_sdk/target_base.py", line 550, in invoke
    target.listen(file_input)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/singer_sdk/io_base.py", line 35, in listen
    self._process_endofpipe()
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/singer_sdk/target_base.py", line 310, in _process_endofpipe
    self.drain_all(is_endofpipe=True)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/singer_sdk/target_base.py", line 470, in drain_all
    self._drain_all(self._sinks_to_clear, 1)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/singer_sdk/target_base.py", line 501, in _drain_all
    self.drain_one(sink)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/singer_sdk/target_base.py", line 495, in drain_one
    sink.process_batch(draining_status)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/singer_sdk/sinks/sql.py", line 267, in process_batch
    self.bulk_insert_records(
  File "/home/visch/git/target-snowflake/target_snowflake/sinks.py", line 142, in bulk_insert_records
    self.insert_batch_files_via_internal_stage(
  File "/home/visch/git/target-snowflake/target_snowflake/sinks.py", line 196, in insert_batch_files_via_internal_stage
    self.connector.copy_from_stage(
  File "/home/visch/git/target-snowflake/target_snowflake/connector.py", line 437, in copy_from_stage
    conn.execute(copy_statement, **kwargs)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/sqlalchemy/engine/base.py", line 1385, in execute
    return meth(self, multiparams, params, _EMPTY_EXECUTION_OPTS)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/sqlalchemy/sql/elements.py", line 334, in _execute_on_connection
    return connection._execute_clauseelement(
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/sqlalchemy/engine/base.py", line 1577, in _execute_clauseelement
    ret = self._execute_context(
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/sqlalchemy/engine/base.py", line 1953, in _execute_context
    self._handle_dbapi_exception(
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/sqlalchemy/engine/base.py", line 2134, in _handle_dbapi_exception
    util.raise_(
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/sqlalchemy/util/compat.py", line 211, in raise_
    raise exception
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/sqlalchemy/engine/base.py", line 1910, in _execute_context
    self.dialect.do_execute(
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/sqlalchemy/engine/default.py", line 736, in do_execute
    cursor.execute(statement, parameters)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/snowflake/connector/cursor.py", line 908, in execute
    Error.errorhandler_wrapper(self.connection, self, error_class, errvalue)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/snowflake/connector/errors.py", line 290, in errorhandler_wrapper
    handed_over = Error.hand_to_other_handler(
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/snowflake/connector/errors.py", line 345, in hand_to_other_handler
    cursor.errorhandler(connection, cursor, error_class, error_value)
  File "/home/visch/git/target-snowflake/.meltano/loaders/target-snowflake/venv/lib/python3.8/site-packages/snowflake/connector/errors.py", line 221, in default_errorhandler
    raise error_class(
sqlalchemy.exc.ProgrammingError: (snowflake.connector.errors.ProgrammingError) 002020 (21S01): 01aeedc2-0001-56f2-0004-428e0003794e: SQL compilation error:
Insert value list does not match column list expecting 13 but got 9
[SQL: copy into RMS_DB.RAW.TEST_SCHEMA_UPDATES from (select $1:id::DECIMAL as id, $1:a1::DECIMAL as a1, $1:a2::VARCHAR as a2, $1:_sdc_extracted_at::TIMESTAMP_NTZ as _sdc_extracted_at, $1:_sdc_received_at::TIMESTAMP_NTZ as _sdc_received_at, $1:_sdc_batched_at::TIMESTAMP_NTZ as _sdc_batched_at, $1:_sdc_deleted_at::TIMESTAMP_NTZ as _sdc_deleted_at, $1:_sdc_sequence::DECIMAL as _sdc_sequence, $1:_sdc_table_version::DECIMAL as _sdc_table_version from '@~/target-snowflake/test_schema_updates-59ad5b95-8dfb-4590-8a2c-41f3c9143dbe')file_format = (format_name='RMS_DB.RAW."test_schema_updates-59ad5b95-8dfb-4590-8a2c-41f3c9143dbe"')]
(Background on this error at: https://sqlalche.me/e/14/f405)

@visch
Copy link
Member

visch commented Sep 12, 2023

As part of #51 I wanted to add a test to assert schema changes when reserved words were used and no key properties were present so the COPY logic would get invoked. It failed and I realized that it would have been failing before my changes in that PR.

This PR adds the test case so we can figure out how to fix it. The problem I saw was that the file in the internal stage matched the initial schema record but by the time it was being loaded into the table the second schema message had already altered the table to the new schema. Ultimately leading to an error related to a mismatch in columns in the table vs stage file columns.

I wonder if the issue here is #116

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
Status: No status
Development

Successfully merging this pull request may close these issues.

3 participants