Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

CAD rakenduste pluginite arendamisel (minu puhul on see AutoCAD, Revit ja Renga) tekib ajaga ĂŒks probleem – ilmuvad uued tarkvara versioonid, nende API muutub ja tuleb teha uued pluginite versioonid.

Kui teil on ainult ĂŒks plugin vĂ”i olete alles algaja, siis saate lihtsalt projekti koopia teha, muuta seal vajalikud kohad ja luua uue pluginiversiooni. Vastavalt sellele toob koodi edasine muutmine kaasa tööjĂ”u vajaduse kordse suurenemise.

Kogemuste ja teadmiste kasvades leiate mitmeid viise selle protsessi automatiseerimiseks. Olen selle tee kÀinud ja tahan jagada teiega, kuhu ma lÔpuks jÔudsin ja kui mugav see on.

Alustame ilmse meetodi arutamisega, mida olen pikka aega kasutanud.

Viidatud projekti failidele

Ja et kÔik oleks lihtne, selge ja arusaadav, kirjeldan kÔike abstraktsel nÀitel pluginite arendamisest.

Avame Visual Studio (mul on Community 2019 versioon. Ja jah – vene keeles) ja loome uue lahenduse. Nimeks anname MySuperPluginForRevit

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Loome plugin Revitile versioonide 2015-2020 jaoks. SeetÔttu loon lahenduses uue projekti (Net Frameworki klasside teek) ja nimetan selle MySuperPluginForRevit_2015

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Peame lisama viidatud Revit API-le. Muidugi saame lisada viidatud kohalikud failid (tuleb endale kĂ”ik vajalikud SDK-d vĂ”i kĂ”ik versioonid Revitist installeerida), kuid me lĂ€heme kohe Ă”igele teele ja lisame NuGet paketi. Te leiate ĂŒsna palju pakette, kuid ma kasutan omaenda.

PĂ€rast paketi ĂŒhendamist klĂ”psame parema hiireklahviga punktile „Viidatud lingidja valime menĂŒĂŒst „Edastada packages.config PackageReference’iks »

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Kui teil peaks selle koha pealt paanikahoog tulema, kuna paketi omaduste aknas ei ole olulist punkti „Kopeeri kohalikultmistĂ”ttu peame selle kindlasti seadistama vÀÀrtuseks false, siis ei maksa paanitseda – lĂ€heme projekti kausta, avame .csproj laiendiga faili sobivas redaktoris (mina kasutan Notepad++) ja otsime seal ĂŒles meie paketi kirje. See nĂ€eb praegu vĂ€lja nii:

1.0.0

Lisame sellele omaduse runtime. Tulemus saab olema jÀrgmine:

1.0.0
  runtime

NĂŒĂŒd, kui projekt on loodud, ei koondata paketi faile vĂ€ljundkausta.
Liigume edasi – eeldame kohe, et meie plugin kasutab midagi Revit API-st, mis on ajas muutunud, kui on vĂ€lja antud uusi versioone. VĂ”i lihtsalt on meil vaja midagi oma koodis muuta sĂ”ltuvalt Revit'i versioonist, mille jaoks me pluginit teeme. Nende koodide erinevuste lahendamiseks kasutame tingimusliku kompileerimise sĂŒmboleid. Avame projekti omadused, liigume sakkidele „Kogumine„ ja vĂ€ljal „Tingimusliku kompileerimise sĂŒmbolid„ kirjutame R2015.

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Pange tĂ€hele, et sĂŒmbol tuleb lisada nii Debug konfiguratsiooni kui ka Release konfiguratsiooni jaoks.

Ja kuna me oleme omaduste aknas, lĂ€heme kohe sakkide „Rakendus„ ja vĂ€ljal „Vaikimisi nimed„ alla ja eemaldame sufiksi _2015, et meie nimi oleks universaalne ja sĂ”ltumatu kogumi nimest:

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Minu puhul ladustatakse kĂ”igi versioonide pluginaid lĂ”ppproduktis ĂŒhte kausta, seega jÀÀvad mu kogumi nimed sufiksiga _20xx. Kuid vĂ”ite eemaldada sufiksi ka kogumi nimest, kui failide asukohti eeldatakse erinevates kaustes.

Liigume faili koodi Class1.cs ja simuleerime seal mingit koodi, arvestades erinevaid Revit'i versioone:

namespace MySuperPluginForRevit
{
    using Autodesk.Revit.Attributes;
    using Autodesk.Revit.DB;
    using Autodesk.Revit.UI;

    [Regeneration(RegenerationOption.Manual)]
    [Transaction(TransactionMode.Manual)]
    public class Class1 : IExternalCommand
    {
        public Result Execute(ExternalCommandData commandData, ref string message, ElementSet elements)
        {
#if R2015
            TaskDialog.Show("ModPlus", "Tere Revit 2015");
#elif R2016
            TaskDialog.Show("ModPlus", "Tere Revit 2016");
#elif R2017
            TaskDialog.Show("ModPlus", "Tere Revit 2017");
#elif R2018
            TaskDialog.Show("ModPlus", "Tere Revit 2018");
#elif R2019
            TaskDialog.Show("ModPlus", "Tere Revit 2019");
#elif R2020
            TaskDialog.Show("ModPlus", "Tere Revit 2020");
#endif
            return Result.Succeeded;
        }
    }
}

Olin kohe arvestanud kĂ”iki Revit'i versioone alates 2015. aastast (millel oli artikkel kirjutamise ajal) ja kohe arvestanud tingimusliku kompileerimise sĂŒmbolite olemasolu, mis luuakse mulle sama malli jĂ€rgi.

Liigume peamise ilu juurde. Loome oma lahendusse uue projekti, ainult Revit 2016 pluginiversioonile. Korrame kĂ”ik ĂŒlaltoodud toimingud, asendades numbreid 2015 numbriga 2016. Kuid faili Class1.cs uusest projektist kustutame.

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Fail, kus on vajalik kood – Class1.cs – meil juba olemas ja meil on vaja lihtsalt sellele uues projektis link lisada. Linkide lisamiseks on kaks teed:

  1. Pikk – parem puudutame projekti paremast hiireklahvist, valime punktilt «Lisa» -> «Olemasolev element», avatud aknas leiame vajaliku faili ja valime variandi «Lisa» asemel valime variandi «Lisa seoseks»

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

  1. LĂŒhike – otse lahenduse sirvijas valime vajaliku faili (vĂ”i isegi faile. VĂ”ime isegi terveid kaustu) ja lohistame uude projektisse, hoides all klahvi Alt. Loome tĂ”mmates nĂ€ete, et alt klahvi all hoides muutub hiirekursor plussmĂ€rkidest nooleks.
    UPD: Ma tegin selle lĂ”iguga veidi segadust — et lohistada mitu faili, tuleb hoida all Shift+Alt!

PĂ€rast protseduuri toimub meil teises projektis fail Class1.cs vastava ikooniga (sinine nool):

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Koodi redigeerimisel redigeerimisaknas saate samuti valida, millise projekti kontekstis koodi kuvada, mis vÔimaldab teil nÀha, kuidas kood erinevate tingimuslike kompileerimise mÀrkide abil redigeeritakse:

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Selle skeemi jĂ€rgi loome kĂ”ik ĂŒlejÀÀnud projektid (2017-2020). Elu nĂ€punĂ€ide – kui lohistada faile lahenduse sirvijas mitte baasprojektist, vaid projektist, kus need on juba ĂŒhendatud, siis ei pea alt klahvi all hoidma!

Kirjeldatud variant on ĂŒsna hea kuni hetkeni, mil lisatakse uus pluginaversioon vĂ”i lisatakse projekti uusi faile – kĂ”ik see muutub vĂ€ga tĂŒĂŒtu. Ja hiljuti taipasin ma Ă€kki, kuidas seda ĂŒhe projektiga lahendada ja liigume teise meetodi juurde.

Konfiguratsioonide maagia

Siia lugedes vĂ”ite exclaimida «Miks sa esimest meetodit kirjeldasid, kui artikkel on kohe teise kohta?!». Kirjutasin ma kĂ”ik selleks, et oleks selgem, mille jaoks me vajame tingimuslikke kompileerimise sĂŒmboleid ja millistes kohtades erinevad meie projektid. Ja nĂŒĂŒd on meil selgem, millised erinevused projektide vahel peame ellu viima, jĂ€ttes ainult ĂŒhe projekti.

Ja et kÔik oleks selgem, me ei loo uut projekti, vaid teeme muudatusi meie praeguses projektis, mis loodi esimesel meetodil.

Nii et, kÔigepealt eemaldame lahendusest kÔik projektid, vÀlja arvatud pÔhiprojekt (millel on otseselt failid). T. e. projektid versioonide 2016-2020 jaoks. Avame kausta lahenduse ja eemaldame seal nende projektide kaustad.

Meil on lahenduses alles jÀÀnud ĂŒks projekt — MySuperPluginForRevit_2015. Avame selle omadused ja:

  1. Vahekaardil «Rakendus» eemaldame kogumi nimest sufiksi _2015 (edasi saate aru, miks)
  2. Vahekaardil «Kogumine» eemaldame tingimusliku kompileerimise sĂŒmboli R2015 to corresponding field

MĂ€rkus: viimasest Visual Studio versioonist leiti viga – tingimuslikud kompileerimise sĂŒmbolid ei kuvata projekti omaduste aknas, kuigi need on olemas. Kui teil on see tĂ”rge, peate need kĂ€sitsi .csproj failist eemaldama. Kuid me peame sellega edasi töötama, seega loeme edasi.

Nimega projekt lahenduse sirvija aknas, kustutame sufiksi _2015 ja seejĂ€rel eemaldame projekti lahendusest. See on vajalik korra sĂ€ilitamiseks ja perfektsionistide tundete jaoks! Avame meie lahenduse kausta, nimetame seal sama moodi projekti kausta ĂŒmber ja laadime projekti tagasi lahendusse.

Avame konfiguratsioonihalduri. Meil on konfiguratsioon Release tÔeliselt ei ole seda vaja, seega eemaldame selle. Loome uusi konfiguratsioone, mille nimed on meile juba tuttavad R2015, R2016, 
, R2020. Pange tÀhele, et parameter ei pea olema teistest konfiguratsioonidest kopeeritud ja projekti konfiguratsioone looma ei pea:

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

LĂ€heme projekti kausta ja avame .csproj laiendiga faili endale sobivas redigeerijas. Üksikasjalikult, seda saab avada ka Visual Studios - projekti tuleb laadida vĂ€lja ja seejĂ€rel otsige kontekstimenĂŒĂŒst vajalik valik:

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Redigeerimine Visual Studios on isegi eelistatum, kuna redigeerija tasandab ja annab vihjeid.

Failis nĂ€eme elemente PropertyGroup – kĂ”ige peal on ĂŒldine, ja seejĂ€rel tingimustega. Need elemendid mÀÀravad projekti omadused selle ĂŒhiselt. Esimene element, mis tingimusteta, mÀÀrab ĂŒldised omadused, ja tingimustega elemendid muudavad vastavalt mĂ”ned omadused konfiguratsioonide pĂ”hjal.

Liigume esimese ĂŒhise elemendi juurde PropertyGroup ja vaatame omadust AssemblyName – see on kogumise nimi ja see peaks olema ilma sufiksita _2015. Kui sufiks on olemas, eemaldame selle.

Leidke tingimusega element

<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">

See ei ole meile vajalik – eemaldame selle.

Tingimusega element

<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">

on vajalik koodi arendamise ja silumise etapi tööks. Saate muuta selle omadusi vastavalt oma vajadustele – mÀÀrata erinevad vĂ€ljundteed, muuta tingimuslikud kompileerimise sĂŒmbolid jne.

NĂŒĂŒd loome uusi elemente PropertyGroup oma konfiguratsioonide jaoks. Nendes elementides on meil piisav mÀÀrata neli omadust:

  • OutputPath – vĂ€ljundkaust. MÀÀran standardvÀÀrtuse binR20xx
  • DefineConstants – tingimisi kompileerimise sĂŒmbolid. Tuleb mÀÀrata vÀÀrtus TRACE;R20xx
  • TargetFrameworkVersion – platvormi versioon. Erinevate Revit API versioonide jaoks peab mÀÀrama erinevad platvormid.
  • AssemblyName – kogumi nimi (st. faili nimi). Saate kirjutada otse vajaliku kogumi nime, kuid universaalsuse huvides soovitan mÀÀrata vÀÀrtuse $(AssemblyName)_20xx. Selleks eemaldasime varem kogumi nimest sufiksi

KÔige olulisem feature nende elementide seas on see, et neid saab lihtsalt kopeerida teistesse projektidesse, muutes need tÀiesti muutumatuks. Edasi artiklis lisan kogu .csproj faili sisu.

Nii, projektide omadustega oleme selgelt toime tulnud – see pole keeruline. Kuid mida teha ĂŒhendatud raamatukogudega (NuGet-pakettidega). Kui vaadata edasi, nĂ€eme, et ĂŒhendatud raamatukogud mÀÀratakse elementidesse ItemGroup. Kuid here on probleem – see element kĂ€sitleb tingimusi valesti, nagu element PropertyGroup. VĂ”ib-olla on see isegi Visual Studio viga, kuid kui mÀÀrata mitu elementi ItemGroup koos konfiguratsiooni tingimustega ja sisestada erinevad viidatud NuGet-pakettide lingid, siis konfiguratsiooni muutmisel lisatakse projekti kĂ”ik mÀÀratud paketid.

Meie abiks tuleb element Vali, mis töötab tuttava loogika jÀrgi if-then-else.

Kasutades elementi Vali, mÀÀrame erinevad NuGet-paketid erinevatele konfiguratsioonidele:

Kogu csproj sisu

Debug
    AnyCPU
    {5AD738D6-4122-4E76-B865-BE7CE0F6B3EB}
    Library
    Properties
    MySuperPluginForRevit
    MySuperPluginForRevit
    v4.5
    512
    true
  
  
    true
    full
    false
    binDebug
    DEBUG;R2015
    prompt
    4
  
  
    binR2015
    TRACE;R2015
    v4.5
    $(AssemblyName)_2015
  
  
    binR2016
    TRACE;R2016
    v4.5
    $(AssemblyName)_2016
  
  
    binR2017
    TRACE;R2017
    v4.5.2
    $(AssemblyName)_2017
  
  
    binR2018
    TRACE;R2018
    v4.5.2
    $(AssemblyName)_2018
  
  
    binR2019
    TRACE;R2019
    v4.7
    $(AssemblyName)_2019
  
  
    binR2020
    TRACE;R2020
    v4.7
    $(AssemblyName)_2020
  
  
    
    
    
    
    
    
    
    
  
  
    
    
  
  
    
      
        
          1.0.0
          runtime
        
      
    
    
      
        
          1.0.0
          runtime
        
      
    
    
      
        
          1.0.0
          runtime
        
      
    
    
      
        
          1.0.0
          runtime
        
      
    
    
      
        
          1.0.0
          runtime
        
      
    
    
      
        
          1.0.0
          runtime

Pange tĂ€hele, et ĂŒhes tingimuses olen ma mĂ€rkinud kaks konfiguratsiooni lĂ€bi VÕI (Or). Seega ĂŒhendatakse vajalik pakett konfiguratsiooni seadistamisel Debug.

Ja nĂŒĂŒd on meil peaaegu kĂ”ik ideaalselt. Laadime projekti tagasi, aktiveerime vajalikku konfiguratsiooni, valime lahenduse (mitte projekti) kontekstimenĂŒĂŒst punkti «Taasta kĂ”ik NuGet paketid» ja nĂ€eme, kuidas meie paketid muutuvad.

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Ja nĂŒĂŒd olen selle etappi jĂ”udnud ummikusse – et koguda kohe kĂ”ik konfiguratsioonid, saaksime kasutada pakettide kogumist (menĂŒĂŒd «Kogumine» -> «Pakettide kogumine»), kuid konfiguratsioonide vahetamisel ei toimu automaatset pakettide taastamist. Ja projekti ehitamisel samuti mitte, kuigi peaks. Selle probleemi lahenduste standardsete vahenditega ma ei leidnud. Ja tĂ”enĂ€oliselt on see samuti Visual Studio viga.

SeetĂ”ttu otsustati pakettide kogumise jaoks kasutada spetsiaalset automatiseeritud kogumise sĂŒsteemi Nuke. Tegelikult ma seda ei tahtnud, kuna pean seda liialdusena pistikprogrammide arendamise raames, kuid praegu ei nĂ€e ma muud lahendust. Ja kĂŒsimusele «Miks just Nuke?» on vastus lihtne – kasutame tööl.

Nii et liigume lahenduse kausta (mitte projekti), hoidke all klahvi Shift ja klĂ”psake hiire parema nupuga kaustas tĂŒhjal kohal – kontekstimenĂŒĂŒst valige punkt «Ava PowerShell aken siin».

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Kui teil ei ole installitud nuke, siis kirjutage esmalt kÀsk

dotnet tool install Nuke.GlobalTool –global

NĂŒĂŒd kirjutage kĂ€sk nuke ja teile pakutakse seadistada nuke praeguse projekti jaoks. Ma ei tea, kuidas seda Ă”igemini eesti keeles kirjutada – inglise keeles oleks kirjutatud Could not find .nuke file. Do you want to setup a build? [y/n]

Vajutame klahvi Y ja edasi tuleb vahetud seadistamise punktid. Meil on vaja kÔige lihtsamat varianti kasutades MSBuild, seega vastame nagu ekraanipildil:

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Liigume Visual Studio'sse, mis pakub meile lahenduse uuesti laadimist, kuna see on lisatud uus projekt. Laadime lahenduse uuesti ja nĂ€eme, et meil on ilmunud projekt build milles meil huvitab ainult ĂŒks fail – Build.cs

Teeme ĂŒhe pistiku projekti erinevate Revit / AutoCAD versioonide all kompileerimisega

Avame selle faili ja kirjutame skripti projekti kogumiseks kÔigi konfiguratsioonide jaoks. VÔi kasutame minu skripti, mida saate endale kohandada:

using System.IO;
using Nuke.Common;
using Nuke.Common.Execution;
using Nuke.Common.ProjectModel;
using Nuke.Common.Tools.MSBuild;
using static Nuke.Common.Tools.MSBuild.MSBuildTasks;

[CheckBuildProjectConfigurations]
[UnsetVisualStudioEnvironmentVariables]
class Build : NukeBuild
{
    public static int Main () => Execute(x => x.Compile);

    [Solution] readonly Solution Solution;

    // If the solution name and the project (plugin) name are different, then indicate the project (plugin) name here
    string PluginName => Solution.Name;

    Target Compile => _ => _
        .Executes(() =>
        {
            var project = Solution.GetProject(PluginName);
            if (project == null)
                throw new FileNotFoundException("Not found!");

            var build = new List();
            foreach (var (_, c) in project.Configurations)
            {
                var configuration = c.Split("|")[0];

                if (configuration == "Debug" || build.Contains(configuration))
                    continue;

                Logger.Normal($"Configuration: {configuration}");

                build.Add(configuration);

                MSBuild(_ => _
                    .SetProjectFile(project.Path)
                    .SetConfiguration(configuration)
                    .SetTargets("Restore"));
                MSBuild(_ => _
                    .SetProjectFile(project.Path)
                    .SetConfiguration(configuration)
                    .SetTargets("Rebuild"));
            }
        });
}

Naasime PowerShelli akn ja jĂ€lle kirjuta kĂ€sku nuke (kĂ€sku saab kirjutada nuke vajalikku mĂ€rkustusega TĂ€ht. Aga meil on ĂŒks TĂ€ht, mis kĂ€ivitub vaikimisi). PĂ€rast Enteri vajutamist tunneme end tĂ”eliste hĂ€kkeritena, kuna nagu filmides toimetatakse meie projekti automaatne koostamine erinevate konfiguratsioonide all.

Muide, PowerShelli saab kasutada otse Visual Studios (menĂŒĂŒs „Vaade» -> «Teised aknad» -> «Pakettide halduri konsool“), kuid seal on kĂ”ik must-valge, mis pole just mugav.

Sellega minu artikkel lĂ”ppeb. Olen kindel, et AutoCAD-i variandi osas saate ise hakkama. Loodan, et siin esitatud materjal leiab oma „kliente”.

AitÀh tÀhelepanu eest!

Allikas: habr.com

Osta usaldusvÀÀrne hostimine veebilehtede jaoks DDoS-i kaitsega, VPS VDS serverid đŸ”„ Osta usaldusvÀÀrne hostimine veebilehtede jaoks DDoS-i kaitsega, VPS VDS serverid | ProHoster