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

Target Date for Widget support? #22

Open
mmaist opened this issue Feb 4, 2020 · 14 comments
Open

Target Date for Widget support? #22

mmaist opened this issue Feb 4, 2020 · 14 comments

Comments

@mmaist
Copy link

mmaist commented Feb 4, 2020

Is there a target date for when widgets will be supported by this newer SDK? I am hesitant to develop on the old SDK and then have to port over to this one, but if the support for widgets isn't coming anytime soon then I'll just bite the bullet.

@Liran-Dobrish
Copy link

i need this feature also, any idea when it might be added?

@meetpatel-promact
Copy link

I also want to know when it will be available, don't want to use the older SDK for the widget contribution.

@yuriburger
Copy link

same here, would be nice to use the new SDK with widgets

@bworline
Copy link

bworline commented Apr 1, 2020

While you're waiting for official support:

I was able to get it to work for a widget and a widget configuration.

I had to make a file that essentially contained the missing bits from vss-web-extension-sdk (several typings from tfs.d.ts and vss.d.ts and a wee bit of implementation from vss.sdk.js - WidgetStatusHelper, WidgetConfigurationSave, ConfigurationEvent) that I couldn't find in
azure-devops-extension-sdk.

When you call SDK.register, pass an IWidget or IConfigurableWidget for a widget, and an IWidgetConfiguration for a widget configuration.

missingSdkBits.zip

@rmouser
Copy link

rmouser commented Oct 7, 2020

Agreed, I also want this because the VSS API forces an ugly coding style, and results in less robust extensions.

@igormcsouza
Copy link

Hello @bworline !! We are trying here to use your file, but we cannot find out where to put this informations or how to call it out to work! Can you give a little of explanation on it!?

@htekdev
Copy link

htekdev commented May 20, 2022

Just started a PR that includes the changes needed to integrate vss-web-extension-sdk into azure-devops-extension-sdk. This would enable widgets using the advised react.js sdk toolkit

#51

Based on my review, everything is there to create a dashboard widget using new SDK. The part that is missing is the logic that consumes the requirejs modules that allow the "legacy" SDK to inject "Dashboard Widget" styles and to use the widget service.

After trying several attempts to move over that logic it seemed simplyer to just "merge" the init phase with both using the same channel. This allows both old and new sdks to be used together. Due to this I was able to create a new method

const WidgetHelpers = await SDK.requireModule<ITFSDashboardsWidgetHelpers>("TFS/Dashboards/WidgetHelpers")

Which is the same as the legacy way:

VSS.require(["TFS/Dashboards/WidgetHelpers"], function (WidgetHelpers: typeof wh) { 
...
})

Now with all of this, I was able to prove everything works with the following full file examples:

vss-extension.json:

{
    "contributions": [
        {
            "id": "AnnotationStatusWidgetV2",
            "type": "ms.vss-dashboards-web.widget",
            "targets": [
                "ms.vss-dashboards-web.widget-catalog"
            ],
            "properties": {
                "name": "Hello World Widget",
                "description": "My first widget",
                "catalogIconUrl": "pipeline-run-annotation-config-hub/img/CatalogIcon.png",
                "previewImageUrl": "pipeline-run-annotation-config-hub/img/preview.png",                            
                "uri": "pipeline-run-annotation-config-hub/dist/AnnotationStatusWidget/AnnotationStatusWidget.html",
                "supportedSizes": [
                     {
                            "rowSpan": 1,
                            "columnSpan": 2
                        }
                    ],
                "supportedScopes": ["project_team"]
            }
        }
    ],
    "scopes": ["vso.work"]
}

Example AnnotationStatusWidget.html:

<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
    <body>
        <div class="widget">
            <div id="root"></div>
        </div>
        <script type="text/javascript" src="AnnotationStatusWidget.js" charset="utf-8"></script>
    </body>
</html>

Example AnnotationStatusWidget.tsx:

import { showRootComponent } from "../../Common";
import * as React from "react";
import * as SDK from "@htekdev/azure-devops-extension-sdk";
import { getAnnotatedRuns, IAnnotatedPipelineRunItem } from "@htekdev/pipeline-run-sdk";
import { FrameworkProvider } from "../../Libs";
import { ITFSDashboardsWidgetHelpers, ITFSDashboardsWidgetContracts } from "@htekdev/azure-devops-extension-sdk";
import {WidgetSettings} from "TFS/Dashboards/WidgetContracts"

type AnnotationStatusWidgetProps = {
    ContributionId: string}
    
const AnnotationStatusWidget : React.FunctionComponent<AnnotationStatusWidgetProps>  = ({ContributionId}) => {
    const [annotatedRuns, setAnnotatedRuns] = React.useState<IAnnotatedPipelineRunItem[]>([]);
    const [error, setError] = React.useState<string | undefined>(undefined)
    
    const load = React.useCallback(async () => {
        try{
            const annotatedRuns = await getAnnotatedRuns(FrameworkProvider, "project")
            setAnnotatedRuns(annotatedRuns)
        }
        catch(e){
            console.log(e);
            setError(`${e}`);
        }
        
    }, [])

    const register = React.useCallback(async () => {
        const WidgetHelpers = await SDK.requireModule<ITFSDashboardsWidgetHelpers>("TFS/Dashboards/WidgetHelpers")
        await WidgetHelpers.IncludeWidgetStyles()

        SDK.register(ContributionId, function () { 
            return {
                load: async (widgetSettings: WidgetSettings) => {
                    try{
                        await load();    
                    }
                    catch(e){
                        console.log(e)
                    }
                    finally{
                        return {
                            statusType: 0
                        }
                    }
                }
            }
        });

        await SDK.notifyLoadSucceeded();
    }, [])

    React.useEffect(() => {
        register()
    }, [ContributionId])
        
    return <>{error ? error : <>{annotatedRuns.length} Annotated Runs</>}</>
}


// Initialize the VSS sdk
SDK.init({
    loaded: false
})


// Initialize the VSS sdk
SDK.ready().then(() => {
    showRootComponent(<AnnotationStatusWidget ContributionId="AnnotationStatusWidgetV2" />);
})


@chriswise01
Copy link

When will this be merged in? This is a key part missing from the SDK.

@htekdev
Copy link

htekdev commented Aug 27, 2022

@chriswise01
Im not sure... I was told the owner is not active so not sure when this will become available...

I published this version though if you want to consume it:
npm install @htekdev/azure-devops-extension-sdk

@syedwastil
Copy link

@htekdev

npm install @htekdev/azure-devops-extension-sdk@2.1.24

Can't find it in npm registry.

@htekdev
Copy link

htekdev commented Sep 28, 2022

@syedwastil so sorry! I had it private. Just published to public registry. Sorry for the delay.
https://www.npmjs.com/package/@htekdev/azure-devops-extension-sdk

@bworline
Copy link

We have a date for widget support: 1/24/2024.

It was added in build 4.231.0 of azure-devops-extension-api with this PR. It may seem odd to not have been added to this SDK package, but I'm told that all contracts for individual areas are now logically part of azure-devops-extension-api. The old SDK (vss-web-extension-sdk) was a combination of both SDK and contracts.

The azure-devops-extension-sample repo has not been updated with an example widget yet, but for now:

To use the new types, import * as Dashboard from 'azure-devops-extension-api/Dashboard';. When you call SDK.register, pass an object that implements IWidget or IConfigurableWidget for a widget, and an IWidgetConfiguration for a widget configuration.

@ImreBoersma
Copy link

ImreBoersma commented Apr 5, 2024

@bworline

To use the new types, import * as Dashboard from 'azure-devops-extension-api/Dashboard';. When you call SDK.register, pass an object that implements IWidget or IConfigurableWidget for a widget, and an IWidgetConfiguration for a widget configuration.

Do you have a working example for this? I'm struggling to get this to work in a Vue.JS app. Thanks in advance!

@bworline
Copy link

bworline commented Apr 25, 2024

@bworline

To use the new types, import * as Dashboard from 'azure-devops-extension-api/Dashboard';. When you call SDK.register, pass an object that implements IWidget or IConfigurableWidget for a widget, and an IWidgetConfiguration for a widget configuration.

Do you have a working example for this? I'm struggling to get this to work in a Vue.JS app. Thanks in advance!

See microsoft/azure-devops-extension-sample#153

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

No branches or pull requests