Giter VIP home page Giter VIP logo

dapplo.jira's Introduction

Dapplo

This is the repository for Dapplo, a modular .NET desktop application.

Sometimes an Windows Store App just can't do what you want, like interact closely with the Operation System. In this case, the solution might be a Dapplo "application".

More to come...

dapplo.jira's People

Contributors

actions-user avatar alfadormx avatar andersand avatar db2222 avatar jlopresti avatar lakritzator avatar lus1n avatar rualert avatar simoncropp avatar uselesstoucan avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar

dapplo.jira's Issues

Expose error messages in exceptions when API calls fail

Discovered originally here in #11:

#11 (comment)

When a call results in a 400/error status code, the JSON returned contains values in the errorMessages and/or errors properties:

{
    "errorMessages":[],
    "errors":{
        "customfield_10017":"Epic Name is required."
    }
}

The resulting exception should expose those error messages.

I suggest that instead of throwing a System.Exception, create and throw a JiraException (or JiraApiException, or something similar) which extends HttpRequestException).

This exception would have a status code (inherited from HttpRequestException) as well as an property of type array/List<string>/IReadOnlyCollection<string> that exposes the errorMessages property as well as a Dictionary<string, string>/IDictionary<string, string>/IReadOnlyDictionary<string, string> that exposes the errors property on the returned JSON.

I'm recommending extending HttpRequestException because that's the exception type that's thrown when a call to EnsureSuccessStatusCode throws an exception.

Creating work log with a "started" field

As per your WorkTests I can successfully run:

var worklog = await Client.Work.CreateAsync(TestIssueKey, new Worklog(TimeSpan.FromHours(16))
{
Comment = "Testing the logging of work"
});

which will create a work log with a comment for that issue. Though if I pass a value into the Started property the work log will still use the current date for Started. I would like to be able to create work logs with a Started value I pass in.

FYI The JIRA REST API shows a "started" date format of "2017-03-15T09:08:51.976+0000", not sure if that helps any. Thanks!

JiraConfig.ExpandGetIssue

Hello,

when I try to get an issue with the renderedFields I got a JsonReaderException exception:

JiraConfig.ExpandGetIssue = new[] { "renderedFields" };
var issue = await Client.Issue.GetAsync(TestIssueKey);

Nachricht:
Newtonsoft.Json.JsonReaderException : Could not convert string to DateTimeOffset: Gestern 1:58 PM. Path 'renderedFields.lastViewed', line 1, position 20629.
Stapelüberwachung:
JsonReader.ReadDateTimeOffsetString(String s)
JsonTextReader.FinishReadQuotedStringValue(ReadType readType)
JsonTextReader.ReadAsDateTimeOffset()

CustomFields are not working

Hi! I tried your code, but issue.Fields.CustomFields.Count returns 0 in every issue.

But the issue does have a lot of customfields. Any help?

Example:

? issue
{Dapplo.Jira.Entities.Issue}
    Changelog: null
    Fields: {Dapplo.Jira.Entities.IssueFields}
    Id: "20265"
    Key: "CRM-2976"
    RenderedFields: null
    Self: {http://jira.engrotec.lokal/rest/api/2/issue/20265}
? issue.Fields.CustomFields.Count
0

But when i open the issue in my browser (http://jira.domain.local/rest/api/2/issue/20265/), i get:

{"expand":"renderedFields,names,schema,operations,editmeta,changelog,versionedRepresentations","id":"20265","self":"http://jira.engrotec.lokal/rest/api/2/issue/20265","key":"CRM-2976","fields":{"customfield_12011":"[email protected]","customfield_13100":null,"customfield_12010":null,"customfield_12013":"www.test.com","customfield_12015":null,"resolution":null,"customfield_12017":null,"customfield_10510":null}}

Thanks in advance!!!

Failed Tests

I start running the test cases on one of our JIRA projects. Here are the results (each post) a test case.

Over all: Is there a way to add a simple call to the TestBase constructor to check for user/pass and avoid all further requests? I normally get blocked when I try to enter the wrong password some times :-)

JIraTests > TestGetServerInfoAsync()

// This should be changed when the title changes
Assert.EndsWith("JIRA", serverInfo.ServerTitle);

Failed: Our ServerTitle ends with "Jira" ... but doesn't really needed to check?

Issue fetching additional issues from JIRA

HI, I have the following issue.

Let's say I want to retrieve a list of all JIRA issues, (currently around 16000 issues). I do know that for my current JIRA implementation, I am limited to retrieving maximum 1000 issues at a time.

However, I cannot figure out a way to retrieve the first 1000, then the second 1000, etc until I have retrieved all 16000.
My current c# code (still in progress) is as follows, where I thought to retrieve the first 1000, then set the start value to the next 1000, but it keeps on returning the first 1000 issues only. How do I go about to do this?

var jiraIssue = jiraClient.Issue;
var searchResult = await jiraIssue.SearchAsync("project in (XXXX) AND (summary ~ Report OR assignee = \"myusername\") AND Status != Closed ORDER BY key ASC", 1000);
do
{
              
                string str = "StartAt: " + searchResult.StartAt.ToString() +
                             "\nMaxResults: " + searchResult.MaxResults.ToString() +
                             "\nTotal: " + searchResult.Total.ToString();
                if (searchResult.IsLast)
                    str = str + "\nIsLast: true";
                else
                    str = str + "\nIsLast: false";
                //MessageBox.Show(str, "Ticket Metrics", MessageBoxButtons.OK, MessageBoxIcon.Information);

                foreach (var issue in searchResult.Issues)
                {
                    listView1.Items.Add(issue.Key);
                }
                searchResult.StartAt += searchResult.MaxResults;
                searchResult = await jiraIssue.SearchAsync("project in (XXXX) AND (summary ~ Report OR assignee = \"myusername\") AND Status != Closed ORDER BY key ASC", 1000);
} while (!searchResult.IsLast);

Optimizable items, about uploading attachments

public static async Task<Attachment> AttachAsync<TContent>(this IAttachmentDomain jiraClient, string issueKey, TContent content, string filename,

Thanks for your help, it saved me a lot of time,
The following are only suggestions for optimizable items, not questions or denials.

As mentioned in the developer article, Jira's attachments can support multiple uploads, and I myself tried PostMan to call the API to test the results, So I think it is possible to support multiple files here, if we want to do.

https://developer.atlassian.com/cloud/jira/platform/rest/v2/api-group-issue-attachments/#api-rest-api-2-issue-issueidorkey-attachments-post

Support for IssueField "SecurityLevel"

Would be also great if you can add the security entitiy to the IssueFields.

API@
api/2/project/{projectKeyOrId}/securitylevel

namespace Dapplo.Jira.Entities
{
  /// <summary>
  ///     Security level information
  /// </summary>
  [JsonObject]
  public class SecurityLevel : BaseProperties<long>
  {
    /// <summary>
    ///     Description for the security level
    /// </summary>
    [JsonProperty("description")]
    public string Description { get; set; }
    
    /// <summary>
    ///     Name of the security level
    /// </summary>
    [JsonProperty("name")]
    public string Name { get; set; }
  }
}

public class IssueFields
{
  /// <summary>
  ///     Security level for this issue
  /// </summary>
  [JsonProperty("security")]
  public SecurityLevel Security { get; set; }
}

Support for "fields" in GetIssue

Can you please add basic support to use "fields" in GetIssue?

public static Task<Issue> GetAsync(this IIssueDomain jiraClient, string issueKey, IEnumerable<string> fields = null, CancellationToken cancellationToken = default)
{
	return jiraClient.GetAsync<Issue, IssueFields>(issueKey, fields, cancellationToken);
}

Thank you

Create issue example.

I'm following the code to create an issue in JIRA.

I'm able to query, search, etc. issues, issue types, projects, etc.

However, when I try and call CreateSync, I keep getting an exception, the status code being 400 and then message being Bad Request.

I'm using the code from IssueTests:

https://github.com/dapplo/Dapplo.Jira/blob/master/Dapplo.Jira.Tests/IssueTests.cs#L50

Is there any way I can see the JSON that is being serialized on the wire, or how I can gain more insight into what's happening here?

Consider the usage of Flurl

At the beginning Flurl(.Http) was not an option, this is why Dapplo.HttpExtensions was written.
Currently the project is well maintained, only a few options seem to missing so it might be usefull to consider using Flurl(.Http) by seeing how far we get and contribute to the project.

Cannot find xunit tests in test explorer

Hi,

Could you please help me out? I have VS Studio 2015 Update 3 Professional with the .NET Core Tools for VS20015. I cannot see the Xunit tests in the Test Runner window. I would like to add some endpoints and the associated tests for them. The problem is I don't see the tests so I cannot execute them. What is your PC configuration?

Thanks
HH

How can I implement ContinueWith?

I'd like to pass a delegate to the search method so that the data is processed when it arrives, avoiding the use of await. Completely running in the background. I'm having trouble implementing it. Here is what I have so far...

    public class Program
    {
        .....
        public void SomeEventFiredOff(object sender, ...)
        {
            SomeStaticClass.PullIssuesByAssignee(UpdateItems); //Call to Dapplo.Jira
        }
        
        //Process results from Dapplo.Jira
        public int UpdateItems(SearchIssuesResult<Issue, JqlIssueSearch> issues)
        {
               foreach (Dapplo.Jira.Entities.Issue issue in issues)
               { 
                  ...
               }
        }
     }
     public static class SomeStaticClass
     {
         //Working
         public void PullIssuesByAssignee(Func<SearchIssuesResult<Issue, JqlIssueSearch>,int> OnComplete)
         {
               ....
               Task<SearchIssuesResult<Issue, JqlIssueSearch>> myAssignedIssues = JiraConnection.Issue.SearchAsync(Where.Assignee.In(usersToWatch));
               myAssignedIssues.Wait(); // <--- how can I not Wait?
               OnComplete(myAssignedIssues.Result);
         }
         //Instead I want to write this code:
         public void PullIssuesByAssignee(Func<SearchIssuesResult<Issue, JqlIssueSearch>,int> OnComplete)
         {
               ....
               Task<SearchIssuesResult<Issue, JqlIssueSearch>> myAssignedIssues = JiraConnection.Issue.SearchAsync(Where.Assignee.In(usersToWatch));
               myAssignedIssues.ContinueWith(  OnComplete(  myAssignedIssues  ) ) // <-- Invalid line
         }
     }

How can I implement ContinueWith, passing it a method such as UpdateItems?

Get Issue with Comments (renderedFields)

Don't have time to take a deeper look. When I try to get an issue with comments and also need the rendered Fields I get a JSON Exception:

Newtonsoft.Json.JsonReaderException : Could not convert string to DateTimeOffset: 14/Dez/20 11:17 AM. Path 'renderedFields.comment.comments[0].created', line 1, position 38695.

I think there is a RenderedComment class missing.

Reference SVG in Dapplo.Jira

The referencing package "SVG" can apparently be removed from Dapplo.Jira.
It's only used in "Dapplo.Jira.SvgWinForms"?

GetSprintsAsync returns IsLastPage as true always

When using GetSprintsAsync, the result set is for MaxItems 50 and IsLastPage is true even though there are more than 100 sprints in board.
When using '/rest/agile/1.0/board/{id}/sprint' directly on browser, I can see isLast is false for initial request.
I am unable to use paging for this request to get all the sprints.

Is there any other way to achieve this?

Disable avatar bitmap functionality

In .NET Core 3.1 (Azure function) I get this error which seems to be related to Avatar bitmap handling.
Is it possible to disable this to avoid dependency on PresentationCore?


   at Dapplo.HttpExtensions.ContentConverter.BitmapSourceHttpContentConverter.CanConvertToHttpContent(Type typeToConvert, Object content) in d:\a\1\s\src\Dapplo.HttpExtensions\ContentConverter\BitmapSourceHttpContentConverter.cs:line 78
   at Dapplo.HttpExtensions.Factory.HttpContentFactory.<>c__DisplayClass3_0.<Create>b__1(IHttpContentConverter x) in d:\a\1\s\src\Dapplo.HttpExtensions\Factory\HttpContentFactory.cs:line 162
   at System.Linq.OrderedEnumerable`1.TryGetFirst(Func`2 predicate, Boolean& found)
   at System.Linq.Enumerable.TryGetFirst[TSource](IEnumerable`1 source, Func`2 predicate, Boolean& found)
   at System.Linq.Enumerable.FirstOrDefault[TSource](IEnumerable`1 source, Func`2 predicate)
   at Dapplo.HttpExtensions.Factory.HttpContentFactory.Create(IHttpBehaviour httpBehaviour, Type inputType, Object content, String contentType) in d:\a\1\s\src\Dapplo.HttpExtensions\Factory\HttpContentFactory.cs:line 162
   at Dapplo.HttpExtensions.Factory.HttpContentFactory.Create(Type inputType, Object content) in 

Improve OAuth support

As documented here: https://jira.atlassian.com/browse/JRA-43171 JIRA doesn't support OAuth 2.0

Today I added OAuth 1.0a support, which I got working and use the information here for testing: https://bitbucket.org/atlassian_tutorial/atlassian-oauth-examples/src/d625161454d1?at=default I used the public key from that repository to setup a test link on my Jira Cloud server, and use the private key in my test case.

The code for testing is here (it's commented out, as the OAuth process opens a browser, which is bad on the test-server) https://github.com/dapplo/Dapplo.Jira/blob/master/Dapplo.Jira.Tests/JiraOAuthTests.cs

I am still looking at a way to make the certificate/private key reading easier, but in a way this is not the job for the library itself...

Custom fields cannot be retrieved

When using below code:
var searchResult = jiraClient.Issue.SearchAsync(Where.Project.In(args[3])).Result;

The custom fields are not populated in the dataset.

Can a parent be set for a subtask?

First, thank you for the work you've put into this project.

That said, is there a way to specify the parent of an issue when setting the issue type to subtask?

From what I can gather here:

https://community.atlassian.com/t5/Jira-questions/Creating-sub-task-from-an-existing-issue-using-API/qaq-p/1275793

The issue type has to be set to "Subtask" (which is easy enough), but I don't see a way to set it through the API.

Is this possible with the current version of thelibrary?

Thanks in advance.

Domain related subclasses

As the API still will grow, and already has a large list of methods, it would help to assign certain methods to their own domain.

E.G. place all methods related to isses in a sub-class "Issue" (needs a name) which is a read-only member property on the JiraApi. The user should call something like: _jiraApi.Issue.GetAsync(); instead of _jiraApi.GetIssueAsync();

Custom fields

As currently we can only get "typed" fields, the custom field are not available.

So check if there is something like the JsonExtensionDataAttribute for the SimpleJson, or maybe this project SHOULD move to Json.NET.

Bad Request response due to Invalid JQL

I'm not sure if i'm creating my query correctly but i am receiving the following error once i added the Or condition

{"errorMessages":["Error in the JQL Query: 'End' is a reserved JQL word. You must surround it in quotation marks to use it in a query. (line 1, character 108)"],"errors":{}}

   var jql = Where.And(
                Where.Project.Is(project),
                Where.Type.In(project.IssueTypes.Where(t => issueTypes.Contains(t.Name)).ToArray()),
                Where.Or(
                    Where.And(
                        Where.Resolved.AfterOrOn.DateTime(startDate),
                        Where.Resolved.BeforeOrOn.DateTime(endDate ?? DateTime.Now)
                    ),
                    Where.Status.Is("End to End Testing")
                )
            );

However when i remove the Or condition it works

            var jql = Where.And(
                Where.Project.Is(project),
                Where.Type.In(project.IssueTypes.Where(t => issueTypes.Contains(t.Name)).ToArray()),
                Where.Resolved.AfterOrOn.DateTime(startDate),
                Where.Resolved.BeforeOrOn.DateTime(endDate ?? DateTime.Now)
            );

How to get all worklogs - "/issue/{issueIdOrKey}/worklog"

Hi, I am not sure if this is the right place for my question. I recently came across an issue, where I discovered the JIRA API only returns 20 worklogs. I wanted to enquire, how, by using Dapplo.JIRA, I can retrieve all worklogs for an issue?

As per last comment here : https://community.atlassian.com/t5/Answers-Developer-Questions/How-do-I-set-maxResults-for-work-logs/qaq-p/543015

One can call "/issue/{issueIdOrKey}/worklog" to retrieve all worklogs, how can one do this using Dapplo.Jira?

Thanks in advance.

Kind Regards,
André

Form designer breaking with Dapplo.Jira installed

Running VS 17.0.6

Create a new Windows Forms .net6 app and add some buttons etc. All if ok

Add nuget of Dapplo.Jira 1.1.42 and then go back to the form. You now cannot click on any control of it you add more controls to the form they just appear at the bottom in the area for non UI controls

Am I doing something wrong here?

2022-02-11 15_06_43-Window

Issue Creation Problem

Hi There,

I am having a bug where when I create an issue using this library, it does not show up on the project hotboard. The issue is created because I can find it when I go to the issues tab, but it is not showing up on the hotboard at all (even after all filters removed, etc.). Has this happened to anyone else, and what was the fix for it?

The basic example throws a 405

I'm using the basic example trying to find a task. I'm getting a 405.

'Response status code does not indicate success: 405 (Method Not Allowed).'

    public string JiraUrl = "https://id.atlassian.com/";
    public string Username = "";
    public string Password = "";

    public IJiraClient Initialize()
    {
        var jiraClient = JiraClient.Create(new Uri(JiraUrl));
        jiraClient.SetBasicAuthentication(Username, Password);
        return jiraClient;
    }

    public async Task FindTask(IJiraClient jiraClient)
    {
        var searchResult = await jiraClient.Issue.SearchAsync(Where.Text.Contains("VIV-2534"));
    }

Custom drop down fields?

I am trying to create an issue with custom fields (drop downs!) but I always get a bad request response upon issue creation.

Custom fields I can set without problems but only string type fields. The two fields I would like to set are drop downs and nothing seems to work for them, the client call always returns a 400 bad request (Exception message: "Field 'Change Reason' cannot be set. It is not on the appropriate screen, or unknown.").

Here is how I try to set such a drop down field:

new Issue { Fields = new IssueFields { CustomFields = { {"customfield_10401", "Sonstiges"} } ...

I am not sure if it's fine to simply pass a string of the drop down item to select as the value. I also tried a single-entry anonymous array and id (e.g. 10305) instead of the value ("Sonstiges") but that didn't change anything. Is it possible to set a custom field that is a combobox?

Btw. the field is definetly available in the issue type (required even). And I can create the issue with a simple Jira CLI client without a problem. The field is also available when I use client.Server.GetFieldsAsync()

Edit Issues

I notice there are no methods on IIssueDomain to edit an issue.

How can I edit an issue?

Estimation field is not necessarily a long value.

I am running in an environment where the estimation field may be null or a double value. This currently causes issues with the long that is expected with the current implementation. I propose that the GetEstimation method be rewritten as a generic, like this:

/// <summary>
///     Retrieve the estimation (story points) from the issue, this only works by using the BoardConfiguration
/// </summary>
/// <param name="boardConfiguration">BoardConfiguration</param>
/// <returns>long with estimation or 0 if nothing</returns>
public long GetEstimation(BoardConfiguration boardConfiguration)
{
    return GetEstimation<long>(boardConfiguration);
}

public T GetEstimation<T>(BoardConfiguration boardConfiguration) 
{
    if (boardConfiguration == null)
    {
        throw new ArgumentNullException(nameof(boardConfiguration));
    }
    var estimationCustomField = boardConfiguration.Estimation.Field.FieldId;
    if (!Fields.CustomFields.ContainsKey(estimationCustomField))
    {
        return default(T);
    }

    var result = Fields.CustomFields[estimationCustomField];

    return result == null ? default(T) : (T)result;
}

client.Issue.SearchAsync Expand on "names" Not Possible

I don't see any way to retrieve the expanded names entity with result from client.Issue.SearchAsync. As you can see, this shows that the names are returned separate from the Issue entity, but there is no property to access them with the result from client.Issue.SearchAsync.

Get Worklogs by User

I would like to see a user's worklogs for the last 7 days.

The issues may not be assigned to the user anymore (or they may never been been assigned since they might have been reviewing).

The only Work method I see for fetching worklogs by Issue Key; I have no way to query by Worklog.

I see that I CAN do the query that I want using issues:

  var startDate = DateTime.Now.AddDays(-7).Date;
  var endDate = DateTime.Now.Date;

  var issues = await jc.Issue.SearchAsync(
      Where.And(
          Where.WorkLogAuthor.IsCurrentUser,
          Where.WorkLogDate.AfterOrOn.DateTime(startDate),
          Where.WorkLogDate.BeforeOrOn.DateTime(endDate)                    
      )
  );

  var worklogTasks = issues.ToDictionary(i => i, i => jc.Work.GetAsync(i.Key));
  Task.WaitAll(worklogTasks.Values.ToArray());
  var userWorklogsByIssue = worklogTasks
      .ToDictionary(i => i.Key,
                    i => i.Value.Result
                      .Where(wl => wl.Author.Name == me.Name)
                      .Where(wl => wl.Started?.DateTime.Date >= startDate)
                      .Where(wl => wl.Started?.DateTime.Date <= endDate)
                      .Where(wl => wl.TimeSpentSeconds > 0)
                      .ToList()
      );

However, shouldn't I be able to query worklogs directly without search issues and then making a separate request for each set of worklogs? Especially since this functionality is available when using the API directly.

How to construct a where clause?

I'm trying to implement a complex where clause, well not too complex. Where the issue is assigned to any of a username and the status != closed.

string [] usersToWatch = ...
SearchAsync(Where.Assignee.In(usersToWatch)

I also see Where.Status.Not but I do not see a way to combine these into a single statement

Retrieve changelogs for an issue

Hi,

I didn't found how to retrieve the changelogs for a given issue in JIRA, is this possible? Or it has not been implemented?

For a JIRA API point of view, I think it has to do with expand=changelog?

Thanks

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.