Skip to main content
Member
April 16, 2026
Question

Need to send data from OneStream to Snowflake using an existing SIC ODBC connection

  • April 16, 2026
  • 7 replies
  • 95 views

Hello,

What is the best way to send data from OneStream to Snowflake using an existing SIC ODBC connection?

Currently I am using SIC ODBC connection to query data from Snowflake and now I would like to send data back to Snowflake.

7 replies

Member
April 17, 2026

If the credentials for the SIC Gateway have permission to insert, update, and/or delete records in a remote dataSource, a OneStream business rule could be leveraged to write-back, update, and/or delete data as needed.

Member
April 22, 2026

SimonHesford​  Thank you!  Would you happen to have any business rule examples?

Member
June 19, 2026

Can you give a little more detail as to what you are trying to do? Built a solution that takes cube view data and write's it directly to snowflake, no flat files. Using a DM step, calls the extender rule to export the cv data, then calls the Smart Integration Function rule

Member
July 8, 2026

Hi, thank you for responding.  I am trying to send actuals data using the current SIC connection to Snowflake.  I already set up the new configuration and data source that can write back to Snowflake through SIC.  Now, I need help with setting up the business rule to update the table in Snowflake.  The data/columns I am using for the test are Scenario, Time, Entity, Account, and Amount.  I found the business rule below as a start, but I have it as an Extensibility Rule and not using the Smart Integration Function.  Can you please share what rule you used to update?

 

Namespace OneStream.BusinessRule.Extender.Writeback

    Public Class MainClass
        Public Function Main(ByVal si As SessionInfo, ByVal globals As BRGlobals, ByVal api As Object, ByVal args As ExtenderArgs) As Object
            Try
                ' 1. Fetch your pre-configured connection directly from the OneStream Configuration file
                ' CHANGE THIS: Replace "YourSnowflakeConfigName" with the exact Connection Name in your config file
                Dim configName As String = "YourSnowflakeConfigName"
                
                Using dbExtConn As DbConnInfo = BRApi.Database.CreateExternalDbConnInfo(si, configName)
                    
                    ' 2. Formulate your data payload table (Replace with your actual Stage/Cube loops)
                    Dim dtWriteBack As New DataTable("SnowflakeStaging")
                    dtWriteBack.Columns.Add("Scenario", GetType(String))
                    dtWriteBack.Columns.Add("Time", GetType(String))
                    dtWriteBack.Columns.Add("Entity", GetType(String))
                    dtWriteBack.Columns.Add("Account", GetType(String))
                    dtWriteBack.Columns.Add("Amount", GetType(Decimal))

                    dtWriteBack.Rows.Add("Actual", "2026M1", "New York", "Net Income", 152500.00)
                    dtWriteBack.Rows.Add("Actual", "2026M1", "Las Vegas", "New Income", 85000.50)

                    ' 3. Stream data via OneStream's native SQL Action Engine
                    Dim targetTable As String = "SF_STAGE_FINANCIALS"
                    
                   ' Loop through your records and execute parameterized Action Queries via the API
For Each row As DataRow In dtWriteBack.Rows
    Dim sqlBuilder As New StringBuilder()
    sqlBuilder.Append("INSERT INTO ").Append(targetTable)
    sqlBuilder.Append(" (Scenario, Time, Entity, Account, Amount) VALUES (")
    sqlBuilder.Append("'").Append(row("Scenario").ToString()).Append("', ")
    sqlBuilder.Append("'").Append(row("Time").ToString()).Append("', ")
    sqlBuilder.Append("'").Append(row("Entity").ToString()).Append("', ")
    sqlBuilder.Append("'").Append(row("Account").ToString()).Append("', ")
    sqlBuilder.Append(Convert.ToDecimal(row("Amount"))).Append(")")
    
    ' Execute action script natively through the established DbConnInfo channel
    BRApi.Database.ExecuteActionQuery(dbExtConn, sqlBuilder.ToString(), True, True)
Next

                    
                    BRApi.ErrorLog.LogMessage(si, "Snowflake writeback processed successfully. Records sent: " & dtWriteBack.Rows.Count)
                End Using

                Return True

            Catch ex As Exception
                Throw New System.Exception("Error in native connection writeback execution: " & ex.Message)
            End Try
        End Function
    End Class
End Namespace

RobbSalzmann
Advisor
Advisor
June 30, 2026

Hi Tyesha,
Here’s an example to help get you started.

Imports System
Imports System.Collections.Generic
Imports System.Data
Imports System.Data.Common
Imports System.Globalization
Imports System.IO
Imports System.Linq
Imports Microsoft.VisualBasic
Imports OneStream.Finance.Database
Imports OneStream.Finance.Engine
Imports OneStream.Shared.Common
Imports OneStream.Shared.Database
Imports OneStream.Shared.Engine
Imports OneStream.Shared.Wcf
Imports OneStream.Stage.Database
Imports OneStream.Stage.Engine

Namespace OneStream.BusinessRule.Extender.SnowflakeActualsExport
Public Class MainClass
Public Function Main(
si As SessionInfo,
globals As BRGlobals,
api As Object,
args As ExtenderArgs) As Object

Try
Select Case args.FunctionType

Case Is = ExtenderFunctionType.Unknown,
ExtenderFunctionType.ExecuteDataMgmtBusinessRuleStep

PushActualsToSnowflake(si)

End Select

Return Nothing

Catch ex As Exception
Throw ErrorHandler.LogWrite(si, New XFException(si, ex))
End Try

End Function

''' <summary>
''' Reads actuals for the current workflow period from the OneStream
''' application database and writes them to Snowflake via the named
''' SIC connection. Deletes existing rows for the period first so the
''' operation is idempotent.
''' </summary>
Private Sub PushActualsToSnowflake(si As SessionInfo)

Try
' workflowTime is a platform-controlled token; interpolation is safe.
Dim workflowTime As String = si.WorkflowClusterPk.WorkflowTimePk.ToString()

Dim readSql As String =
$"SELECT Account, Entity, Amount
FROM XFW_Actuals
WHERE WorkflowTime = '{workflowTime}'"

Dim deleteSql As String =
$"DELETE FROM ONESTREAM_ACTUALS WHERE WORKFLOW_TIME = '{workflowTime}'"

' Read source rows from the OneStream application database.
Dim sourceData As DataTable
Using appConnection As DbConnInfo =
BRApi.Database.CreateApplicationDbConnInfo(si)

sourceData = BRApi.Database.ExecuteSqlUsingReader(appConnection, readSql, True)

End Using

' Write to Snowflake via the named SIC connection.
Using snowflakeConnection As DbConnInfo =
BRApi.Database.CreateExternalDbConnInfo(si, "Snowflake")

' Clear existing rows for this period before reloading.
BRApi.Database.ExecuteActionQuery(snowflakeConnection, deleteSql, Nothing, False)

' Insert one row per source record. Account, entity, and amount
' are internal application database values; workflowTime is a
' platform token. Both are safe to interpolate.
For Each row As DataRow In sourceData.Rows

Dim account As String = Convert.ToString(row("Account"), CultureInfo.InvariantCulture)
Dim entity As String = Convert.ToString(row("Entity"), CultureInfo.InvariantCulture)
Dim amount As String = Convert.ToDecimal(row("Amount")).ToString(CultureInfo.InvariantCulture)

Dim insertSql As String =
$"INSERT INTO ONESTREAM_ACTUALS (ACCOUNT, ENTITY, AMOUNT, WORKFLOW_TIME)
VALUES ('{account}', '{entity}', {amount}, '{workflowTime}')"

BRApi.Database.ExecuteSql(snowflakeConnection, insertSql, Nothing, False)

Next

End Using

Catch ex As Exception
Throw New XFException(
si, $"Failed to push actuals to Snowflake. WorkflowTime={si.WorkflowClusterPk.WorkflowTimePk}", ex)
End Try

End Sub
End Class
End Namespace

 

Member
July 8, 2026

Thank you!  I will give this a try.

OneStream Employee
July 7, 2026

Just for information,

using the SIC connection to Snowflake (if using ODBC) you are constrained to write back using INSERT commands as explained in the example above, which can be perfectly fine for not-too-large datasets. If you need to push back larger quantities of data, you might have to take an alternate approach which consists of sending data out in a file, to either Snowflake stage or any other file repositories supported by Snowflake, then issue a command to Snowflake to go and ingest that content which will then process the contente in bulk mode. If you need more assistance with this, our Remote Consulting team can assist you if you log a case through the Service Now Portal.

 

Joakim