Skip to content

Build Intelligent Apps with RAI

With the RAI Native App installed in Snowflake, you can use the relationalai Python package to turn stacks of data into a web of meaning—by modeling the entities, relationships, and rules that drive your application.

  1. Create a model.

    First, import relationalai and create a Model object:

    supply_chain_model.py
    import relationalai as rai
    model = rai.Model("SupplyChainModel")

    Then, use model.Type() to define entity types derived from your Snowflake tables, and .define() to model the relationships between them.

    For example, a simple supply chain model might have the following entity types and relationships:

    supply_chain_model.py
    import relationalai as rai
    model = rai.Model("SupplyChainModel")
    # DECLARE ENTITY TYPES.
    # You can declare entity types from Snowflake tables. Data from these tables
    # are used to answer queries about the model.
    Product = model.Type("Product", source="<my_db>.<my_schema>.products")
    Order = model.Type("Order", source="<my_db>.<my_schema>.orders")
    Supplier = model.Type("Supplier", source="<my_db>.<my_schema>.suppliers")
    # DEFINE RELATIONSHIP PROPERTIES
    # "Product contained_in Order" where Product.id == Order.product_id
    Product.define(contained_in=(Order, "id", "product_id"))
    # Properties can be one-to-one or one-to-many.
    Product.contained_in.has_many()
    # "Order fulfilled_by Supplier" where Order.supplier_id == Supplier.id
    # fulfilled_by is a one-to-one relationship since .has_many() is not called.
    Order.define(fulfilled_by=(Supplier, "supplier_id", "id"))

    Now you can use the model.rule() context manager to define rules that generate new entities and properties based on what you’ve already modeled:

    supply_chain_model.py
    import relationalai as rai
    from relationalai.std import aggregates # <-- Add this line>
    model = rai.Model("SupplyChainModel")
    Product = model.Type("Product", source="<my_db>.<my_schema>.products")
    Supplier = model.Type("Supplier", source="<my_db>.<my_schema>.suppliers")
    Order = model.Type("Order", source="<my_db>.<my_schema>.orders")
    # DECLARE A NEW ENTITY TYPE.
    SingleSourceProduct = model.Type("SingleSourceProduct")
    8 collapsed lines
    # "Product contained_in Order" where Product.id == Order.product_id
    Product.define(contained_in=(Order, "id", "product_id"))
    # Properties can be one-to-one or one-to-many.
    Product.contained_in.has_many()
    # "Order fulfilled_by Supplier" where Order.supplier_id == Supplier.id
    # fulfilled_by is a one-to-one relationship since .has_many() is not called.
    Order.define(fulfilled_by=(Supplier, "supplier_id", "id"))
    # WRITE A RULE TO DEFINE THE NEW ENTITY TYPE.
    # "Product is SingleSourceProduct" if it has exactly one Supplier
    with model.rule():
    product = Product()
    supplier = product.supplied_by
    aggregates.count(supplier, per=[product]) == 1
    product.set(SingleSourceProduct)
    # WRITE A RULE TO DEFINE A NEW PROPERTY.
    # "Product supplied_by Supplier" where Product.contained_in.fulfilled_by == Supplier
    with model.rule():
    product = Product()
    order = product.contained_in
    supplier = order.fulfilled_by
    product.supplied_by.add(supplier)
  2. Use a Reasoner.

    You can extend your model further by using reasoners with advanced AI capabilities to uncover insights that traditional SQL can’t express.

    For example, you can import the relationalai.std.graphs module to use RAI’s graph reasoner to analyze relationships between entities in your model, such as identifying suppliers who sell similar products:

    supply_chain_model.py
    import relationalai as rai
    from relationalai.std import aggregates, graphs # <-- Edit this line
    model = rai.Model("SupplyChainModel")
    Product = model.Type("Product", source="<my_db>.<my_schema>.products")
    Supplier = model.Type("Supplier", source="<my_db>.<my_schema>.suppliers")
    Order = model.Type("Order", source="<my_db>.<my_schema>.orders")
    SingleSourceProduct = model.Type("SingleSourceProduct")
    # DECLARE A NEW ENTITY TYPE.
    SimilarSuppliers = model.Type("SimilarSuppliers")
    22 collapsed lines
    # "Product contained_in Order" where Product.id == Order.product_id
    Product.define(contained_in=(Order, "id", "product_id"))
    # Properties can be one-to-one or one-to-many.
    Product.contained_in.has_many()
    # "Order fulfilled_by Supplier" where Order.supplier_id == Supplier.id
    # fulfilled_by is a one-to-one relationship since .has_many() is not called.
    Order.define(fulfilled_by=(Supplier, "supplier_id", "id"))
    # "Product is SingleSourceProduct" if it has exactly one Supplier
    with model.rule():
    product = Product()
    supplier = product.supplied_by
    aggregates.count(supplier, per=[product]) == 1
    product.set(SingleSourceProduct)
    # "Product supplied_by Supplier" where Product.contained_in.fulfilled_by == Supplier
    with model.rule():
    product = Product()
    order = product.contained_in
    supplier = order.fulfilled_by
    product.supplied_by.add(supplier)
    # DEFINE A GRAPH.
    graph = graphs.Graph(model, undirected=True)
    # Define nodes from the union of the Product and Supplier types.
    graph.Node.extend(Product | Supplier)
    # Define edges between Products and their Suppliers
    graph.Edge.extend(Product.supplied_by)
    # WRITE A RULE THAT USES THE GRAPH TO DEFINE THE NEW ENTITY TYPE.
    # Conditionally define SimilarSuppliers using the Jaccard similarity algorithm.
    with model.rule():
    supplier1, supplier2 = Supplier(), Supplier()
    score = graph.compute.jaccard_similarity(supplier1, supplier2)
    score > 0.5
    suppliers = SimilarSuppliers.add(supplier1=supplier1, supplier2=supplier2)
    suppliers.set(similarity_score=score)
  3. Query the model and export data.

    Query your model using the model.query() context manager to get a pandas DataFrame with the results:

    supply_chain_model.py
    import relationalai as rai
    from relationalai.std import aggregates, alias, graphs # <-- Edit this line
    model = rai.Model("SupplyChainModel")
    47 collapsed lines
    # Declare entity types.
    Product = model.Type("Product", source="<my_db>.<my_schema>.products")
    Supplier = model.Type("Supplier", source="<my_db>.<my_schema>.suppliers")
    Order = model.Type("Order", source="<my_db>.<my_schema>.orders")
    # Types without source tables must be defined later in a rule.
    SingleSourceProduct = model.Type("SingleSourceProduct")
    SimilarSuppliers = model.Type("SimilarSuppliers")
    # Define relationship properties.
    # "Product contained_in Order" where Product.id == Order.product_id
    Product.define(contained_in=(Order, "id", "product_id"))
    # Properties can be one-to-one or one-to-many.
    Product.contained_in.has_many()
    # "Order fulfilled_by Supplier" where Order.supplier_id == Supplier.id
    # fulfilled_by is a one-to-one relationship since .has_many() is not called.
    Order.define(fulfilled_by=(Supplier, "supplier_id", "id"))
    # Define rules to derive new entities and properties.
    # "Product is SingleSourceProduct" if it has exactly one Supplier
    with model.rule():
    product = Product()
    supplier = product.supplied_by
    aggregates.count(supplier, per=[product]) == 1
    product.set(SingleSourceProduct)
    # "Product supplied_by Supplier" where Product.contained_in.fulfilled_by == Supplier
    with model.rule():
    product = Product()
    order = product.contained_in
    supplier = order.fulfilled_by
    product.supplied_by.add(supplier)
    # Define a graph.
    graph = graphs.Graph(model, undirected=True)
    # Define nodes from the union of the Product and Supplier types.
    graph.Node.extend(Product | Supplier)
    # Define edges between Products and their Suppliers
    graph.Edge.extend(Product.supplied_by)
    # Conditionally define SimilarSuppliers using the Jaccard similarity algorithm.
    with model.rule():
    supplier1, supplier2 = Supplier(), Supplier()
    score = graph.compute.jaccard_similarity(supplier1, supplier2)
    score > 0.5
    suppliers = SimilarSuppliers.add(supplier1=supplier1, supplier2=supplier2)
    suppliers.set(similarity_score=score)
    # QUERY THE MODEL.
    # What are the potential backup suppliers for products with a single supplier?
    with model.query() as select:
    product = SingleSourceProduct()
    supplier = product.supplied_by
    potential_supplier = SimilarSuppliers(supplier1=supplier).supplier2
    response = select(
    alias(product.id, "product_id"),
    alias(potential_supplier.id, "potential_supplier_id"),
    )
    # USE THE RESULTS AS A PANDAS DATAFRAME.
    response.results.head(5)

Kickstart your RAI journey with sample notebooks for real-world examples and use cases.

Deepen your understanding of RelationalAI with our comprehensive guides that cover core concepts, basic functionality, and advanced topics.