{"id":28062,"date":"2024-06-14T05:00:00","date_gmt":"2024-06-14T03:00:00","guid":{"rendered":"https:\/\/sii.pl\/blog\/?p=28062"},"modified":"2024-06-06T11:05:51","modified_gmt":"2024-06-06T09:05:51","slug":"wersjonowanie-d365-aktualizacja-deskryptora-z-uzyciem-powershell-i-devops","status":"publish","type":"post","link":"https:\/\/sii.pl\/blog\/wersjonowanie-d365-aktualizacja-deskryptora-z-uzyciem-powershell-i-devops\/","title":{"rendered":"Wersjonowanie D365 \u2013 aktualizacja deskryptora z u\u017cyciem PowerShell i DevOps"},"content":{"rendered":"\n<p>Bazuj\u0105c na swoim do\u015bwiadczeniu, zesp\u00f3\u0142 zajmuj\u0105cy si\u0119 <a href=\"https:\/\/sii.pl\/oferta\/enterprise-software\/dynamics-365\/\" target=\"_blank\" aria-label=\" (opens in a new tab)\" rel=\"noreferrer noopener\" class=\"ek-link\">Microsoft Dynamics 365<\/a> Finance and Operations przygotowa\u0142 kilkana\u015bcie modyfikacji (modeli) do aplikacji, kt\u00f3re w g\u0142\u00f3wnej mierze dotycz\u0105 dostosowa\u0144 do <a href=\"https:\/\/eur05.safelinks.protection.outlook.com\/?url=https%3A%2F%2Fappsource.microsoft.com%2Fpl-pl%2Fmarketplace%2Fapps%3Fsearch%3Dsii%2520Sp.%2520z%2520o.o.%26page%3D1&amp;data=05%7C02%7Cmwitkowski2%40sii.pl%7Cd00f9767f3124c18462e08dc0dc2b832%7Cf9bd6df6c449481fabb537bd036beb76%7C0%7C0%7C638400377156069593%7CUnknown%7CTWFpbGZsb3d8eyJWIjoiMC4wLjAwMDAiLCJQIjoiV2luMzIiLCJBTiI6Ik1haWwiLCJXVCI6Mn0%3D%7C3000%7C%7C%7C&amp;sdata=h%2F0xuX%2BBJB7oq4P7s9xQxHOEnxuz5HpOoAXsksz7Mw8%3D&amp;reserved=0\" target=\"_blank\" aria-label=\" (opens in a new tab)\" rel=\"noreferrer noopener\" class=\"ek-link\" rel=\"nofollow\" >wymog\u00f3w polskiego prawa<\/a>. Niestety nasze prawo nie s\u0142ynie ze stabilno\u015bci, co poci\u0105ga za sob\u0105 konieczno\u015b\u0107 ci\u0105g\u0142ych poprawek i prac nad narz\u0119dziami.<\/p>\n\n\n\n<p>Po rozdystrybuowaniu modeli w\u015br\u00f3d klient\u00f3w stan\u0119li\u015bmy przed wyzwaniem, jakim by\u0142o dok\u0142adna identyfikacja wersji naszych produkt\u00f3w, a co za tym idzie \u2013 mo\u017cliwo\u015b\u0107 szybkiego udzielenia pomocy. Oczywi\u015bcie najprostszym rozwi\u0105zaniem jest r\u0119czne zarz\u0105dzanie numerami modeli. Jednak\u017ce modele koegzystuj\u0105 w \u015brodowisku, s\u0105 \u0142\u0105czone (buildowane), a nast\u0119pnie testowane w r\u00f3\u017cnych konfiguracjach, wi\u0119c <strong>numer ostatniej poprawki w pojedynczej modyfikacji nie by\u0142 wystarczaj\u0105cy.<\/strong><\/p>\n\n\n\n<p>Potrzebna by\u0142a <strong>cecha<\/strong>, kt\u00f3ra z jednej strony pozwoli na sprawdzenie wersji pojedynczej funkcjonalno\u015bci, a z drugiej pomo\u017ce sprawdzi\u0107, czy ta wersja jest \u201ekompatybilna\u201d z innymi. Z artyku\u0142u dowiecie si\u0119, jak j\u0105 znalaz\u0142em.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\"><strong>Problem<\/strong><\/h2>\n\n\n\n<p>W CC Dynamics 365 pojawi\u0142 si\u0119 pomys\u0142 na aktualizacj\u0119 wersji podczas build. Nie znalaz\u0142em gotowego narz\u0119dzia, kt\u00f3re przed wykonaniem build zaktualizowa\u0142oby wersj\u0119 w deskryptorze zapisanym w xml. Numer wersji mia\u0142 posiada\u0107 numer changeseta ostatniej zmiany. Deskryptor dla D365 zapisany w formacie xml wed\u0142ug zamierze\u0144 ma zawiera\u0107 informacje o wersji jak ni\u017cej:<\/p>\n\n\n\n<figure class=\"wp-block-image aligncenter size-large\"><a href=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/1.jpg\"><img decoding=\"async\" width=\"1050\" height=\"155\" src=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/1-1024x151.jpg\" alt=\"Informacje o wersji w deskryptorze\" class=\"wp-image-28063\" srcset=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/1-1024x151.jpg 1024w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/1-300x44.jpg 300w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/1-768x113.jpg 768w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/1.jpg 1050w\" sizes=\"(max-width: 1050px) 100vw, 1050px\" \/><\/a><figcaption class=\"wp-element-caption\">Ryc. 1 Informacje o wersji w deskryptorze<\/figcaption><\/figure>\n\n\n\n<h2 class=\"wp-block-heading\"><strong>Koncepcja<\/strong><\/h2>\n\n\n\n<p>Ten przypadek jest wykonywany podczas build z u\u017cyciem Microsoft-Hosted Agent w Azure DevOps Pipelines. Aktualizacja wersji zostanie wykonana jako krok w pipeline przez skrypt napisany w PowerShell z wykorzystaniem Rest API. Repozytorium jest w TFVC.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\"><strong>Dzia\u0142anie skryptu<\/strong><\/h3>\n\n\n\n<figure class=\"wp-block-image aligncenter size-large\"><a href=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image2.png\"><img decoding=\"async\" width=\"1024\" height=\"223\" src=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image2-1024x223.png\" alt=\"Dzia\u0142anie skryptu\" class=\"wp-image-28065\" srcset=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image2-1024x223.png 1024w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image2-300x65.png 300w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image2-768x167.png 768w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image2-1536x335.png 1536w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image2-2048x446.png 2048w\" sizes=\"(max-width: 1024px) 100vw, 1024px\" \/><\/a><figcaption class=\"wp-element-caption\">Ryc. 2 Dzia\u0142anie skryptu<\/figcaption><\/figure>\n\n\n\n<h3 class=\"wp-block-heading\"><strong>Autoryzacja<\/strong><\/h3>\n\n\n\n<p>Aby zweryfikowa\u0107 numer changeseta ostatniej zmiany dla konkretnego modelu i zrobi\u0107 checkin zmian dla pliku deskryptora, u\u017cywam polece\u0144 kontroli wersji Team Foundation z poziomu PowerShell, autoryzuj\u0105c si\u0119 przez token OAuth. Korzystaj\u0105c z DevOps pipelines, nale\u017cy pami\u0119ta\u0107 o wyra\u017ceniu zgody na dost\u0119p do OAuth token przez zmienn\u0105 System.AccessToken. Dzi\u0119ki takiemu rozwi\u0105zaniu autoryzacja przebiegnie bez wy\u015bwietlania okna logowania oraz podawania nazwy u\u017cytkownika i has\u0142a.<\/p>\n\n\n\n<figure class=\"wp-block-image aligncenter size-full\"><a href=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image4.png\"><img decoding=\"async\" width=\"854\" height=\"124\" src=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image4.png\" alt=\"Autoryzacja\" class=\"wp-image-28067\" srcset=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image4.png 854w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image4-300x44.png 300w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image4-768x112.png 768w\" sizes=\"(max-width: 854px) 100vw, 854px\" \/><\/a><figcaption class=\"wp-element-caption\">Ryc. 3 Autoryzacja<\/figcaption><\/figure>\n\n\n\n<h3 class=\"wp-block-heading\"><strong>Weryfikacja autora zmiany<\/strong><\/h3>\n\n\n\n<p>Sprawdzenie autora zmiany odbywa si\u0119 przez Rest API, a autoryzacja z wykorzystaniem PAT. Osobisty token dost\u0119pu powinien mie\u0107 pe\u0142ne uprawnienia do odczytywania, zapisywania i zarz\u0105dzania kodem oraz repozytorium.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\"><strong>Zadania<\/strong><\/h2>\n\n\n\n<p>Pierwszym krokiem jest wygenerowanie listy modeli zawieraj\u0105cych plik deskryptora, kt\u00f3ry ma zosta\u0107 zaktualizowany. W tym przypadku sprawdzi\u0142o si\u0119 wylistowanie katalog\u00f3w przez Get-ChildItem, wskazuj\u0105c \u015bcie\u017ck\u0119 Metadata w repozytorium.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">$Solutions = @(Get-childitem Metadata)<\/pre>\n\n\n\n<p>P\u0119tla Foreach uruchamia si\u0119 dla ka\u017cdego wylistowanego modelu osobno i zawiera zadania wymienione w dalszej cz\u0119\u015bci artyku\u0142u.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">Foreach ($Solution in $Solutions) {\r\n\u2026\r\n}\r\n<\/pre>\n\n\n\n<p>Ostatni\u0105 zmian\u0119 mo\u017cna zweryfikowa\u0107 komend\u0105 <em>tf history<\/em>, kt\u00f3ra po dodaniu parametru <em>\/stopafter:1<\/em> wska\u017ce informacj\u0119 o ostatniej zmianie w formie tabeli. Z pomoc\u0105 PowerShell nale\u017cy zapisa\u0107 jedynie numer changeseta do zmiennej (w tym przypadku <em>$SolutionVersion)<\/em> (po wi\u0119cej informacji <a href=\"https:\/\/learn.microsoft.com\/en-us\/azure\/devops\/repos\/tfvc\/use-team-foundation-version-control-commands?view=azure-devops\" target=\"_blank\" aria-label=\" (opens in a new tab)\" rel=\"noreferrer noopener\" class=\"ek-link\" rel=\"nofollow\" >odsy\u0142am do artyku\u0142u<\/a>). \u00a0<\/p>\n\n\n\n<p>Kolejnym krokiem jest weryfikacja autora zmiany, aby wykluczy\u0107 zmiany wprowadzone przez u\u017cytkownika \u201eBuild Service\u201d, kt\u00f3ry dokonuje aktualizacji deskryptora podczas uruchomienia zautomatyzowanego pipeline. U\u017cywaj\u0105c Rest API i polecenia GET, zostanie zwr\u00f3cona informacja o autorze changseta konkretnego pliku w repozytorium. (po wi\u0119cej informacji <a href=\"https:\/\/learn.microsoft.com\/en-us\/rest\/api\/azure\/devops\/tfvc\/changesets\/get-changesets?view=azure-devops-rest-7.0&amp;tabs=HTTP\" target=\"_blank\" aria-label=\" (opens in a new tab)\" rel=\"noreferrer noopener\" class=\"ek-link\" rel=\"nofollow\" >odsy\u0142am do artyku\u0142u<\/a>).<\/p>\n\n\n\n<p>Po wskazaniu \u015bcie\u017cki deskryptora nale\u017cy uruchomi\u0107 p\u0119tl\u0119 Foreach oraz instrukcj\u0119 if wykluczaj\u0105c\u0105 wy\u017cej wspominanego u\u017cytkownika \u201eBuild Service\u201d i wprowadzi\u0107 zmiany w pliku xml, u\u017cywaj\u0105c wcze\u015bniej utworzonej zmiennej z numerem changeseta. VersionBuild, VersionMajor i VersionMinor zostaj\u0105 zaktualizowane z u\u017cyciem Get-Date.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">foreach ($DescriptorFile in $DescriptorPath) {\r\nif ($result.author.displayName -ne \"ProjectName Build Service (OrganizationName)\") {\r\n\r\n$Day = (Get-Date).day # VersionBuild\r\n$Month = (Get-date).month # VersionMajor\r\n$Year = (Get-Date).year # VersionMinor \r\n\r\n$xml = New-Object XML\r\n$xml.Load($file)\r\n$VersionBuild = $xml.SelectSingleNode(\"\/\/VersionBuild\")\r\n$VersionBuild.InnerText = $Day\r\n$VersionMajor = $xml.SelectSingleNode(\"\/\/VersionMajor\")\r\n$VersionMajor.InnerText = $Year\r\n$VersionMinor = $xml.SelectSingleNode(\"\/\/VersionMinor\")\r\n$VersionMinor.InnerText = $Month\r\n$VersionRevision = $xml.SelectSingleNode(\"\/\/VersionRevision\")\r\n$VersionRevision.InnerText = $SolutionVersion\r\n$xml.Save($file)\r\n}\r<\/pre>\n\n\n\n<p>W instrukcji else pozostaj\u0105 obecne warto\u015bci ostatniego changeseta, natomiast warto\u015bci zawieraj\u0105ce dat\u0119 zostaj\u0105 zaktualizowane.<\/p>\n\n\n\n<p>Na ko\u0144cu instrukcji if oraz else, nale\u017cy u\u017cy\u0107 komendy tf checkin do zatwierdzenia zmian w deskryptorze.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">tf checkin $DescriptorFile \/comment:\"Updated model $Solution version to $Day.$Month.$Year.$SolutionVersion in $SolutionDescriptor\"<\/pre>\n\n\n\n<p>Po zatwierdzeniu zmian wersja zostaje zaktualizowana. W przypadku zmiany wykonanej przez Build Service aktualizacja numeru changseta jest pomijana.<\/p>\n\n\n\n<figure class=\"wp-block-image aligncenter size-full\"><a href=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image5-1.png\"><img decoding=\"async\" width=\"674\" height=\"214\" src=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image5-1.png\" alt=\"Repozytorium DevOps\" class=\"wp-image-28069\" srcset=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image5-1.png 674w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image5-1-300x95.png 300w\" sizes=\"(max-width: 674px) 100vw, 674px\" \/><\/a><figcaption class=\"wp-element-caption\">Ryc. 4 Repozytorium DevOps<\/figcaption><\/figure>\n\n\n\n<figure class=\"wp-block-image aligncenter size-full\"><a href=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image6.png\"><img decoding=\"async\" width=\"247\" height=\"57\" src=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image6.png\" alt=\"Plik deskryptora\" class=\"wp-image-28071\"\/><\/a><figcaption class=\"wp-element-caption\">Ryc. 5 Plik deskryptora<\/figcaption><\/figure>\n\n\n\n<figure class=\"wp-block-image aligncenter size-full\"><a href=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image7-1.png\"><img decoding=\"async\" width=\"773\" height=\"556\" src=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image7-1.png\" alt=\"Update model parameters Visual Studio\" class=\"wp-image-28073\" srcset=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image7-1.png 773w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image7-1-300x216.png 300w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image7-1-768x552.png 768w\" sizes=\"(max-width: 773px) 100vw, 773px\" \/><\/a><figcaption class=\"wp-element-caption\">Ryc. 6 Update model parameters Visual Studio<\/figcaption><\/figure>\n\n\n\n<p>U\u017cywaj\u0105c opisanego skryptu, nale\u017cy pami\u0119ta\u0107 o wy\u0142\u0105czeniu innych krok\u00f3w zwi\u0105zanych z wersjonowaniem w pipeline.<\/p>\n\n\n\n<figure class=\"wp-block-image aligncenter size-full\"><a href=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image8.png\"><img decoding=\"async\" width=\"476\" height=\"94\" src=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image8.png\" alt=\"Wersjonowanie\" class=\"wp-image-28075\" srcset=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image8.png 476w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image8-300x59.png 300w\" sizes=\"(max-width: 476px) 100vw, 476px\" \/><\/a><figcaption class=\"wp-element-caption\">Ryc. 7 Wersjonowanie<\/figcaption><\/figure>\n\n\n\n<p>Po wdro\u017ceniu paczki na \u015brodowisko D365 mo\u017cesz sprawdzi\u0107 wersj\u0119 modelu, korzystaj\u0105c z platformy.<\/p>\n\n\n\n<figure class=\"wp-block-image aligncenter size-full\"><a href=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image9-1.png\"><img decoding=\"async\" width=\"433\" height=\"796\" src=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image9-1.png\" alt=\"Sprawdzenie wersji modelu\" class=\"wp-image-28077\" srcset=\"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image9-1.png 433w, https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/image9-1-163x300.png 163w\" sizes=\"(max-width: 433px) 100vw, 433px\" \/><\/a><figcaption class=\"wp-element-caption\">Ryc. 8 Sprawdzenie wersji modelu<\/figcaption><\/figure>\n\n\n\n<h2 class=\"wp-block-heading\"><strong>Zako\u0144czenie<\/strong><\/h2>\n\n\n\n<p>Artyku\u0142 przedstawia moje rozwi\u0105zanie przedstawionego we wst\u0119pie problemu z dok\u0142adn\u0105 identyfikacj\u0105 wersji naszych produkt\u00f3w. Poza od\u015bwie\u017caniem tokenu PAT skrypt nie wymaga\u0142 ode mnie jakichkolwiek dzia\u0142a\u0144. Skrypt, jako krok w pipeline, uruchamiany jest cyklicznie przed ka\u017cdym build. Wszelkie zamierzenia zosta\u0142y spe\u0142nione.<\/p>\n\n\n\n<p>***<\/p>\n\n\n\n<p>Je\u015bli interesuje Ci\u0119 tematyka Dynamics 365, zajrzyj koniecznie do<a href=\"https:\/\/sii.pl\/blog\/all\/dynamics-365\/\" target=\"_blank\" aria-label=\" innych artyku\u0142\u00f3w naszych autor\u00f3w (opens in a new tab)\" rel=\"noreferrer noopener\" class=\"ek-link\"> innych artyku\u0142\u00f3w naszych autor\u00f3w<\/a>. <\/p>\n\n\n<div class=\"kk-star-ratings kksr-auto kksr-align-left kksr-valign-bottom\"\n    data-payload='{&quot;align&quot;:&quot;left&quot;,&quot;id&quot;:&quot;28062&quot;,&quot;slug&quot;:&quot;default&quot;,&quot;valign&quot;:&quot;bottom&quot;,&quot;ignore&quot;:&quot;&quot;,&quot;reference&quot;:&quot;auto&quot;,&quot;class&quot;:&quot;&quot;,&quot;count&quot;:&quot;28&quot;,&quot;legendonly&quot;:&quot;&quot;,&quot;readonly&quot;:&quot;&quot;,&quot;score&quot;:&quot;5&quot;,&quot;starsonly&quot;:&quot;&quot;,&quot;best&quot;:&quot;5&quot;,&quot;gap&quot;:&quot;11&quot;,&quot;greet&quot;:&quot;&quot;,&quot;legend&quot;:&quot;5\\\/5 ( votes: 28)&quot;,&quot;size&quot;:&quot;18&quot;,&quot;title&quot;:&quot;Wersjonowanie D365 \u2013 aktualizacja deskryptora z u\u017cyciem PowerShell i DevOps&quot;,&quot;width&quot;:&quot;139.5&quot;,&quot;_legend&quot;:&quot;{score}\\\/{best} ( {votes}: {count})&quot;,&quot;font_factor&quot;:&quot;1.25&quot;}'>\n            \n<div class=\"kksr-stars\">\n    \n<div class=\"kksr-stars-inactive\">\n            <div class=\"kksr-star\" data-star=\"1\" style=\"padding-right: 11px\">\n            \n\n<div class=\"kksr-icon\" style=\"width: 18px; height: 18px;\"><\/div>\n        <\/div>\n            <div class=\"kksr-star\" data-star=\"2\" style=\"padding-right: 11px\">\n            \n\n<div class=\"kksr-icon\" style=\"width: 18px; height: 18px;\"><\/div>\n        <\/div>\n            <div class=\"kksr-star\" data-star=\"3\" style=\"padding-right: 11px\">\n            \n\n<div class=\"kksr-icon\" style=\"width: 18px; height: 18px;\"><\/div>\n        <\/div>\n            <div class=\"kksr-star\" data-star=\"4\" style=\"padding-right: 11px\">\n            \n\n<div class=\"kksr-icon\" style=\"width: 18px; height: 18px;\"><\/div>\n        <\/div>\n            <div class=\"kksr-star\" data-star=\"5\" style=\"padding-right: 11px\">\n            \n\n<div class=\"kksr-icon\" style=\"width: 18px; height: 18px;\"><\/div>\n        <\/div>\n    <\/div>\n    \n<div class=\"kksr-stars-active\" style=\"width: 139.5px;\">\n            <div class=\"kksr-star\" style=\"padding-right: 11px\">\n            \n\n<div class=\"kksr-icon\" style=\"width: 18px; height: 18px;\"><\/div>\n        <\/div>\n            <div class=\"kksr-star\" style=\"padding-right: 11px\">\n            \n\n<div class=\"kksr-icon\" style=\"width: 18px; height: 18px;\"><\/div>\n        <\/div>\n            <div class=\"kksr-star\" style=\"padding-right: 11px\">\n            \n\n<div class=\"kksr-icon\" style=\"width: 18px; height: 18px;\"><\/div>\n        <\/div>\n            <div class=\"kksr-star\" style=\"padding-right: 11px\">\n            \n\n<div class=\"kksr-icon\" style=\"width: 18px; height: 18px;\"><\/div>\n        <\/div>\n            <div class=\"kksr-star\" style=\"padding-right: 11px\">\n            \n\n<div class=\"kksr-icon\" style=\"width: 18px; height: 18px;\"><\/div>\n        <\/div>\n    <\/div>\n<\/div>\n                \n\n<div class=\"kksr-legend\" style=\"font-size: 14.4px;\">\n            5\/5 ( votes: 28)    <\/div>\n    <\/div>\n","protected":false},"excerpt":{"rendered":"<p>Bazuj\u0105c na swoim do\u015bwiadczeniu, zesp\u00f3\u0142 zajmuj\u0105cy si\u0119 Microsoft Dynamics 365 Finance and Operations przygotowa\u0142 kilkana\u015bcie modyfikacji (modeli) do aplikacji, kt\u00f3re &hellip; <a class=\"continued-btn\" href=\"https:\/\/sii.pl\/blog\/wersjonowanie-d365-aktualizacja-deskryptora-z-uzyciem-powershell-i-devops\/\">Continued<\/a><\/p>\n","protected":false},"author":644,"featured_media":28083,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"_editorskit_title_hidden":false,"_editorskit_reading_time":0,"_editorskit_is_block_options_detached":false,"_editorskit_block_options_position":"{}","inline_featured_image":false,"footnotes":""},"categories":[1314],"tags":[1546,1512,576,646],"class_list":["post-28062","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-development-na-twardo","tag-przeglad-narzedzi","tag-poradnik","tag-dynamics-365","tag-dynamics-365-finance-and-operations"],"acf":[],"aioseo_notices":[],"republish_history":[],"featured_media_url":"https:\/\/sii.pl\/blog\/wp-content\/uploads\/2024\/06\/Aktualizacja-deskryptora-z-uzyciem-PowerShell-i-DevOps.jpg","category_names":["Development na twardo"],"_links":{"self":[{"href":"https:\/\/sii.pl\/blog\/wp-json\/wp\/v2\/posts\/28062"}],"collection":[{"href":"https:\/\/sii.pl\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/sii.pl\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/sii.pl\/blog\/wp-json\/wp\/v2\/users\/644"}],"replies":[{"embeddable":true,"href":"https:\/\/sii.pl\/blog\/wp-json\/wp\/v2\/comments?post=28062"}],"version-history":[{"count":2,"href":"https:\/\/sii.pl\/blog\/wp-json\/wp\/v2\/posts\/28062\/revisions"}],"predecessor-version":[{"id":28082,"href":"https:\/\/sii.pl\/blog\/wp-json\/wp\/v2\/posts\/28062\/revisions\/28082"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/sii.pl\/blog\/wp-json\/wp\/v2\/media\/28083"}],"wp:attachment":[{"href":"https:\/\/sii.pl\/blog\/wp-json\/wp\/v2\/media?parent=28062"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/sii.pl\/blog\/wp-json\/wp\/v2\/categories?post=28062"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/sii.pl\/blog\/wp-json\/wp\/v2\/tags?post=28062"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}