Code Monkey home page Code Monkey logo

Comments (10)

stoiveyp avatar stoiveyp commented on September 24, 2024 1

aplDocumentJson and dataDocumentJson would be objects - most likely JObject objects. That could be parsed from a string, loaded from a stream or read from a blob in cloud storage

from alexa.net.apl.

stoiveyp avatar stoiveyp commented on September 24, 2024 1

Have you tried directive.Properties.Add("dataSources",sources); to see if it's the JObject conversion?

from alexa.net.apl.

stoiveyp avatar stoiveyp commented on September 24, 2024

I tried to make the names descriptive in the example - aplDocumentJson is the JSON for the APL document, so if you crafted something using the APL online designer, you can send it without having to map it to the APL model (unless you want to be able to alter it, for example)

As you're crafting a directive using JSON - if you wanted both the document and the dataSources, you'd add the document property as per the example as well as the dataSources property with your data source JSON in it - there's an example of a JSON directive with data sources here

https://developer.amazon.com/en-GB/docs/alexa/alexa-presentation-language/apl-interface.html#renderdocument-directive

Hope that makes sense

from alexa.net.apl.

aalmada avatar aalmada commented on September 24, 2024

@stoiveyp What was confusing me was that the Add takes an object and didn't figure out it is building a JSON document.

Is it something like this?

var aplDocumentJson = " { ... }";
var dataDocumentJson =  = "{ ... }";
var directive = new JsonDirective(RenderDocumentDirective.APLDirectiveType);
directive.Properties.Add("document",aplDocumentJson);
directive.Properties.Add("dataSources",dataDocumentJson);

You do make the names descriptive but I'm not yet into the context of the Alexa API. I only post an issue/question as a last resource and I'm very sorry for taking you time.

Thank you so much for developing all these libraries.

from alexa.net.apl.

aalmada avatar aalmada commented on September 24, 2024

I succeed in having the APL in a JSON file.

  1. Added the file to an "APL" subfolder.
  2. Added the following to the csproj:
    <None Update="APL/*.json">
      <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
    </None>
  1. Added a parameter ExecutionContext executionContext to the function, as explained here.
  2. Added the following code:
var executionPath = Directory.GetParent(executionContext.FunctionDirectory).FullName;
var directive = new JsonDirective(RenderDocumentDirective.APLDirectiveType);
directive.Properties.Add("document", JObject.Parse(await File.ReadAllTextAsync(Path.Combine(executionPath,"APL", "launch.json"))));
directive.Properties.Add("dataSources", JObject.Parse("..."));

from alexa.net.apl.

stoiveyp avatar stoiveyp commented on September 24, 2024

Okay. Are we okay to close now then?

from alexa.net.apl.

aalmada avatar aalmada commented on September 24, 2024

I'm reopening because I cannot make the "dataSources" property appear in the directive. I already tried many variants.

For my latest attempt, I developed this method that creates the APL directive given an JObject with the template and the data sources, as an array of pairs containing a string and an ObjectDataSource:

static JsonDirective CreateAplDirective(JObject apl, params (string Key, ObjectDataSource Value)[] dataSources)
{
    var directive = new JsonDirective(RenderDocumentDirective.APLDirectiveType);

    directive.Properties.Add("document", apl);

    var sources = new Dictionary<string, ObjectDataSource>();
    foreach (var (key, dataSource) in dataSources)
        sources.Add(key, dataSource);

    directive.Properties.Add("dataSources", JObject.FromObject(sources));

    return directive;
}

I expected it to serialized to the format specified in the link you shared. The "document" property is serialized with no issues but the "dataSources" property is never serialized.

As a reference, here's the code calling the method:

static async Task<IActionResult> HandleLaunchRequest(APLSkillRequest request, ILogger log, string executionPath)
{
    log.LogInformation("Handle LaunchRequest");

    var response = ResponseBuilder
        .Ask("Welcome to my skill. How can I help", new Reprompt());

    if (request.APLSupported())
    {
        var json = await File.ReadAllTextAsync(Path.Combine(executionPath,"APL", "launch.json"));
        var launchTemplateApl = JObject.Parse(json);

        var launchTemplateData = new ObjectDataSource
        {
            ObjectId = "launchScreen",
            Properties = new Dictionary<string, object>(),
            TopLevelData = new Dictionary<string, object>(),
        };
        launchTemplateData.Properties.Add("textContent", "My Skill");
        launchTemplateData.Properties.Add("hintText", "Try, \"What can you do?\"");

        var directive = CreateAplDirective(launchTemplateApl, ("launchTemplateData", launchTemplateData));

        response.Response.Directives.Add(directive);
    }

    return new OkObjectResult(response);
}

Note that the properties Properties and TopLevelData for the ObjectDataSource have to be assigned or, it will throw a null exception.

from alexa.net.apl.

aalmada avatar aalmada commented on September 24, 2024

Still doesn't work. But, yes, the JObject.FromObject() in unnecessary.

from alexa.net.apl.

stoiveyp avatar stoiveyp commented on September 24, 2024

I've just ran the code you posted with two changes

  • I had to remove the if statement (I didn't have a request to use)
  • Instead of OkObjectResult I used var output = JsonConvert.SerializeObject(response); because I was running it in the Alexa.NET.APL test project.

The output is below - with both a document and dataSources property. If you aren't seeing it in your output then there's something happening in the response of your skill stopping that from happening.

What I do notice straight away is that the type property is wrong - which one of the community has coincidentally raised this morning as a PR into Alexa.NET - you will need to bump the version of Alexa.NET you're using when it's merged in, so you can keep an eye on it here:

timheuer/alexa-skills-dotnet#194

"directives": [
            {
                "Type": "Alexa.Presentation.APL.RenderDocument",
                "document": {
                    "type": "APL",
                    "theme": "dark",
                    "version": "1.2",
                    "mainTemplate": null
                },
                "dataSources": {
                    "launchTemplateData": {
                        "type": "object",
                        "objectID": "launchScreen",
                        "properties": {
                            "textContent": "My Skill",
                            "hintText": "Try, \"What can you do?\""
                        }
                    }
                }
            }
        ]

If you could run the JsonConvert line I've mentioned and see if you also get the dataSources property appear, that would help us figure out where the problem you're having is.

from alexa.net.apl.

aalmada avatar aalmada commented on September 24, 2024

Found it! My fault again... 😒

It looks like Alexa discards anything that does not recognize. The test tab doesn't show what receives. Only parts of it.

I had a copy/paste bug. I copied the variable name into the string so, these was an upper-case S. "dataSources" instead of "datasources"... 😱

Here's the method to generate the APL directive. It may be helpful for others:

static JsonDirective CreateAplDirective(string token, object apl, params (string, ObjectDataSource)[] dataSources)
{
    var directive = new JsonDirective(RenderDocumentDirective.APLDirectiveType);

    if (!string.IsNullOrEmpty(token))
        directive.Properties.Add("token", token);

    directive.Properties.Add("document", apl);

    if (dataSources.Length != 0)
    {
        var sources = new Dictionary<string, ObjectDataSource>();
        foreach (var (key, dataSource) in dataSources)
            sources.Add(key, dataSource);

        directive.Properties.Add("datasources", sources);
    }

    return directive;
}

Having to initialize the properties Properties and TopLevelData for the ObjectDataSource seems to me to be an issue that should be fixed.

from alexa.net.apl.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.