Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

...

SkilledKnowledgeableAware

ThingModel - Create ThingModels that combines ThingFacet,

ThingFacet - Create ThingFacet for devices based on protocol supported out of the box

Attribute - Ability to define attributes of Primitive and complex (Custom types)

Action - Write Action with standard Workflow that invokes out of the box protocols.

DataModel - Create "Pure" Data only models to capture just enough data attributes to be associated with Things.

Model and model Instances - Deploying models and creating instances of model. Entire lifecycle

of models.

Query (including model to model) - Write queries (CRUD) to be used by app developers, use queries form within models.

Subscription (including model to model) - External websocket based subscription. Subscribe to model changes from within the model.

Building HTML/JavaScript apps - Create standard simple HTML/JS applications.

Scheduling - Schedule piece of TQL code to be executed at scheduled interval.

Macros - What are macros and how they are useful.

Standard System Macros (Pipeline Macros)

 

FacetScript -

Temporary Cache - Context, Facet, Local, Process Data Stores

Deployment package - How is standard TQLStudio Projects deployed

Template Processor - How to process message responses. Use of XPath expressions

   
Code Block
languagexml
titleTQL101 Skills
linenumberstrue
collapsetrue
<Namespace Name="Atomiton">

  <Domain Name="TQL101">

    <Def Name="PostalAddress">

      <String Name="StreetName"/>

      <String Name="City"/>

      <String Name="State"/>

      <String Name="Zipcode"/>

    </Def>

    

    <DataModel Name="Room">

      <Sid Name="RoomID"/>

      <String Name="RoomName"/>

      <Integer Name="RoomSize"/>

      <Reference Name="HouseID" Type="House" Cardinality="1"/>

    </DataModel>

    <DataModel Name="House">

      <Sid Name="HouseID"/>

      <String Name="Owner"/>

      <PostalAddress Name="Address"/>

    </DataModel>

    <ThingFacet Name="TempFacetSerial">

      <PeripheralParams Name="PerifParams"/>

      <String Name="SensorData" update="auto" KnownBy="SensorDataReadAction"/>

      <String Name="ScheduleCalc" KnownBy="ScheduleCalcAction"/>

      <String Name="InitSubscribers" default="false" KnownBy="InitSubAction"/>

      <Integer Name="BaseTemp"/>

      <Integer Name="PctChange"/>

      <String Name="Calculated"/>

      <String Name="SensorURL" Default="phid://"/>

      <String Name="SensorInterfaceIndex"/>

      <String Name="SensorType"/>

      <String Name="SensorInterfaceType"/>

      <String Name="SensorValueFormat"/>

      <String Name="Simulated"/>

      <DateTime Name="Timestamp" Format="$SimpleDateFormat(yyyy-MM-dd'T'HH:mm:ss'Z')"/>

      <Action Name="SensorDataReadAction" Documentation="Sync the value of Sensors from Phidget Interface 8/8/8">

        <Workflow Limit="1" Live="1" Timeout="-1">

          <Task Name="Main" While="true">

            <Event Name="Argument" As="ActionArgument"/>

            <Invoke Name="ReadValue" waitFor="Argument" Get="[%:Event.Argument.SensorURL.Value:%][%:Event.Argument.SensorInterfaceIndex.Value:%]"

              SerialNumber="[%:Event.Argument.SensorInterfaceIndex.Value:%]" DeviceType="[%:Event.Argument.SensorInterfaceType.Value:%]" SensorValueFormat="[%:Event.Argument.SensorValueFormat.Value:%]"

              SensorType="[%:Event.Argument.SensorType.Value:%]" MessagesPerSecond="5" Simulated="[%:Event.Argument.Simulated.Value:%]"/>

            <Output Name="Result" As="ActionResult">

              <Value>

                <SensorData>

                  TEMPC:0#TEMPF:[%:[%:@Output:%]Invoke.ReadValue.Message.Value:%]#HUMPCT:0#AMB:0

                </SensorData>

              </Value>

            </Output>

          </Task>

        </Workflow>

      </Action>

      

      

      <Action Name="ScheduleCalcAction" Documentation="Start reading temperature from source and calc new value">

        <Workflow Limit="1" Live="1" Timeout="-1">

          <Task Name="Main1" While="true">

            <Event Name="Argument" As="ActionArgument"/>

            <Invoke Name="StartSimulation" waitFor="Argument">

              <FacetScript>

                <If condition="/'[%:Event.Argument.ScheduleCalc.Value:%]' eq 'true'">

                  <then>

                    <Log Message="Starting calculation..[%:Event.Argument.SensorID:%]"/>

                    <ScheduleJob>

                      <JobName>

                        CalcTempValue[%:Event.Argument.SensorID:%]

                      </JobName>

                      <ScheduleInterval>

                        1min

                      </ScheduleInterval>

                      <ActionCode>

                        <CalculateBaseTempValue>

                          <DstTempSensorId>

                            [%:Event.Argument.SensorID:%]

                          </DstTempSensorId>

                        </CalculateBaseTempValue>

                      </ActionCode>

                    </ScheduleJob>

                  </then>

                  <else>

                    <Log Message="Stopping calculation.."/>

                    <DeleteScheduleJob>

                      <JobName>

                        CalcTempValue[%:Event.Argument.SensorID:%]

                      </JobName>

                    </DeleteScheduleJob>

                  </else>

                </If>

              </FacetScript>

            </Invoke>

            <Output Name="Result" As="ActionResult">

              <Value>

                <ScheduleCalc>

                  [%:Event.Argument.ScheduleCalc.Value:%]

                </ScheduleCalc>

              </Value>

            </Output>

          </Task>

        </Workflow>

      </Action>

      <Action Name="InitSubAction">

        <Workflow Limit="1" Live="1" Timeout="-1">

          <Task name="Main" while="true">

            <Event name="Argument" as="ActionArgument"/>

            <Invoke name="InvokeSubs" waitFor="Argument">

              <FacetScript>

                <If Condition="/'[%:Event.Argument.InitSubscribers.Value:%]' eq 'true'">

                  <Log Message="Subscribing to: *Atomiton.TQL101.TempSensor.SensorData.[%:Event.Argument.SensorId:%]*"/>

                  <SubscribeToTQL>

                    <TopicName>*Atomiton.TQL101.TempSensor.SensorData.[%:Event.Argument.SensorId:%]*</TopicName>

                    <ActionName>

                      <ParseAndUpdateBaseTemp>

                        <SensorID>[%:Event.Argument.SensorId:%]</SensorID>

                      </ParseAndUpdateBaseTemp>

                    </ActionName>

                  </SubscribeToTQL>

                </If>

              </FacetScript>

            </Invoke>

            <Output Name="Result" As="ActionResult">

              <Value>

                <InitSubscribers>

                  [%:Event.Argument.InitSubscribers.Value:%]

                </InitSubscribers>

              </Value>

            </Output>

          </Task>

        </Workflow>

      </Action>

    </ThingFacet>

    <ThingModel Name="TempSensor" combines="TempFacetSerial">

      <Sid Name="SensorID"/>

      <Reference Name="RoomID" Type="Room" Cardinality="1"/>

    </ThingModel>







    <Macro Name="SubscribeToTQL">

      <Argument>

        <TopicName>TQL.*</TopicName>

        <TopicId>GenericTopicID</TopicId>

        <ActionName/>

      </Argument>

      <Result>

        <DoRequest target="[:RuntimeParams.TopicFacetIDName:]" Disable="CMD_SERVER">

          <Process return="CMD_NOP">

            <Message type="xml">

              <Value>

                <Subscribe sid="[:$Macro.Argument.TopicId:]" topic="[:$Macro.Argument.TopicName:]">

                  <Action>

                    [:$Macro.Argument.ActionName:]

                  </Action>

                </Subscribe>

              </Value>

            </Message>

          </Process>

        </DoRequest>

      </Result>

    </Macro>




    <Macro Name="DeleteScheduleJob">

      <Argument>

        <JobName/>

      </Argument>

      <Result>

        <DoRequest target="[:$RuntimeParams.SequenceFacetIDName:]" Disable="CMD_SERVER">

          <Process return="CMD_NOP">

            <Message type="xml">

              <Value>

                <Remove eid="[:$Macro.Argument.JobName:]"/>

              </Value>

            </Message>

          </Process>

        </DoRequest>

      </Result>

    </Macro>







    <Macro Name="ScheduleJob">

      <Argument>

        <ScheduleInterval></ScheduleInterval>

        <StartTime>0</StartTime>

        <EndTime></EndTime>

        <ActionCode></ActionCode>

        <JobName></JobName>

      </Argument>

      <Result>

        <DoRequest target="[:RuntimeParams.SequenceFacetIDName:]" Disable="CMD_SERVER">

          <Process return="CMD_NOP">

            <Message>

              <Value>

                <Execute eid="[:$Macro.Argument.JobName:]" schedule="[[:$Macro.Argument.StartTime:]..[:$Macro.Argument.EndTime:]/[:$Macro.Argument.ScheduleInterval:]]">

                  <Action>

                    <ExecuteQuery>

                      <QueryString>

                        [:$Macro.Argument.ActionCode:]

                      </QueryString>

                    </ExecuteQuery>

                  </Action>

                </Execute>

              </Value>

            </Message>

          </Process>

        </DoRequest>

      </Result>

    </Macro>




    <Macro Name="ExecuteQuery">

      <Argument>

        <QueryString>

          <Query/>

        </QueryString>

      </Argument>

      <Result>

        <DoRequest Target="[:RuntimeParams.FacetIDName:]" Disable="CMD_SERVER">

          <Process return="CMD_NOP">

            <Message>

              <Value>[:$Macro.Argument.QueryString:]</Value>

            </Message>

          </Process>

        </DoRequest>

      </Result>

    </Macro>




    <Macro Name="UpdateBaseTempValue">

      <Argument>

        <TempSensorId/>

        <TempF/>

      </Argument>

      <Result>

        <ExecuteQuery>

          <QueryString>

            <Query>

              <Find format="version">

                <TempSensor>

                  <SensorID eq="[:$Macro.Argument.TempSensorId:]"/>

                </TempSensor>

              </Find>

              <SetResponseData>

                <Key>Message.Value.Find.Result.TempSensor.BaseTemp.Value</Key>

                <Value>[:$Macro.Argument.TempF:]</Value>

              </SetResponseData>

              <Update>

                <From>Result</From>

                <Include>$Response.Message.Value.Find</Include>

              </Update>

            </Query>

          </QueryString>

        </ExecuteQuery>

        <DelResponseData key="Message.Value.Find"/>

      </Result>

    </Macro>




    <Macro Name="CalculateBaseTempValue">

      <Argument>

        <DstTempSensorId/>

      </Argument>

      <Result>

        <Log Message="Calculating Base Temp Value for.... [:$Macro.Argument.DstTempSensorId:]"/>

        <ExecuteQuery>

          <QueryString>

            <Query>

              <Find format="version">

                <Room as="var.Room">

                  <RoomName eq="Hall"/>

                </Room>

                <TempSensor>

                  <RoomID eq="var.Room.RoomID"/>

                </TempSensor>

              </Find>

            </Query>

          </QueryString>

        </ExecuteQuery>




        <SetContextData Key="MainTempValue" Value="[:$Response.Message.Value.Find.Result.TempSensor.BaseTemp.Value:]"/>




        <ExecuteQuery>

          <QueryString>

            <Query>

              <Find format="version">

                <TempSensor>

                  <SensorID eq="[:$Macro.Argument.DstTempSensorId:]"/>

                </TempSensor>

              </Find>

            </Query>

          </QueryString>

        </ExecuteQuery>




        <SetContextData Key="PctChange" Value="[:$Response.Message.Value.Find.Result.TempSensor.PctChange.Value:]"/>




        <Log Message="Main Temp Value is.. [:$ContextData.MainTempValue:]"/>

        <Log Message="PctChange Value is.. [:$ContextData.PctChange:]"/>

        <JavaScript>

          var bTemp = [:$ContextData.MainTempValue:];

          var pct = [:$ContextData.PctChange:];

          var tempV = bTemp + (pct/100)*bTemp;

          sffLog.info("NewTempValue is:..." + tempV);

          sffContext.execute(&quot;SetContextData&quot;,&quot;key&quot;,&quot;NewTempValue&quot;,&quot;value&quot;,tempV);

        </JavaScript>




        <Log Message="Calcualted Value is..[:$ContextData.NewTempValue:]"/>

        <UpdateBaseTempValue>

          <TempSensorId>[:$Response.Message.Value.Find.Result.TempSensor.SensorID:]</TempSensorId>

          <TempF>[:$ContextData.NewTempValue:]</TempF>

        </UpdateBaseTempValue>




        <DelContextData Key="MainTempValue"/>

        <DelContextData Key="NewTempValue"/>




        <SetResponseData Key="Response.Message.Value.Status" Value="Success"/>

        <SetResponseData Key="Response.Message.Value.Message" Value="[:$ContextData.NewTempValue:]"/>

      </Result>

    </Macro>




    <Macro Name="ParseAndUpdateBaseTemp">

      <Argument>

        <SensorID/>

      </Argument>

      <Result>

        <ExecuteQuery>

          <QueryString>

            <Query>

              <Find format="all">

                <TempSensor>

                  <SensorID eq="[:$Macro.Argument.SensorID:]"/>

                </TempSensor>

              </Find>

            </Query>

          </QueryString>

        </ExecuteQuery>

        <SetContextData Key="SData" Value="[:$Response.Message.Value.Find.Result.TempSensor.SensorData.Known:]"/>

        <JavaScript>

          var str = "[:$ContextData.SData:]";

          sffLog.info("***************SensorData**************" + str);

          var

          sensorToken =

          str.split("#");

          var

          updateBaseTemp = ListMap.static.newInstance();

          for(i=0; i&lt;sensorToken.length; i++) {

          sval

          =sensorToken[i].split(":");

          if (sval[0] ==

          "TEMPF") {

          var upQ =

          updateBaseTemp.instanceAdd("UpdateBaseTempValue");

          upQ.put("TempSensorId",

          "[:$Macro.Argument.SensorID:]");

          upQ.put("TempF",

          sval[1]);

          break;

          }

          }

          sffLog.info(updateBaseTemp);

          updateBaseTemp;

        </JavaScript>

        <DelContextData Key="SData"/>

      </Result>

    </Macro>

  </Domain>

</Namespace>