How to sync version numbers for nuget packages when targeting multiple project files - versioning

I have a project which has three project files targeting various .net versions (mylib.net20.csproj, mylib.net40.csproj, and mylib.net40-client.csproj). I have a single nuspec file named mylib.nuspec for packaging them all together.
It might help to see the files section of the nuspec file, so here it is:
<files>
<file src="bin\net20\*.dll" target="lib\net20\" />
<file src="bin\net40-client\*.dll" target="lib\net40-client\" />
<file src="bin\net40\*.dll" target="lib\net40\" />
</files>
Right now I use a static version number in the nuspec file and I can successfully package everything by running nuget pack mylib.nuspec. However, I would like to start using $version$ so I don't have to remember to update the version number in two places.
If I simply change the version number to $version$, and build in the same way I get the predictable error:
Attempting to build package from 'mylib.nuspec'.
The replacement token 'version' has no value.
If I use $version$ and package with nuget pack mylib.net40.csproj, it is successful, but I get a package that completely ignores the nuspec file.
Q: What can I do to get the $version$ variable to work?
Technically, I could rename my nuspec file to mylib.net20.nuspec and then package with nuget pack mylib.net20.nuspec. I really don't want to rename my nuspec file in this way though.

creating a package can be done two ways
Using nuspec directly
Using your csproj file , which in fact uses your nuspec file at run time.
First case is pretty straight forward where all metadata defined in nuspec file will be considered for package creation.
nuget pack nuspecfilename.nuspec
On executing above command all hard coded values in your nuspec file will be used for package creation
Above Procedure uses nuspec file directly.
Now let come to your requirement , Using token $version$ in your nuspec files.
In order to work with tokens rather than hard coded values , we need to use csproj file while running nuget pack command.
nuget pack nameofyourprojectfile.csproj -p "configuration=Release;platform=x64"
I'll explain the command i have used ,the concept of using csproj file while generating a package is it will replace all tokens in nuspec file at the run time.
Your corresponding assembly info file to your csproj file will contain required metadata of version which will be replaced at run time.
-p is parameters to be used at run time , here i have assumed that my proj file builds in release and x64 platform so i have passed that at run time so nuget which for artifacts to bundle accordingly.
please refer Here for more details on how to create nuget packages from csproj.
But Ideally when you package from csproj file your nuspec file will be used at run time so ,technically nuspec file should have same name as that of your csproj file.
so requirement of dealing with multiple project files with different frame work may not be achieved with single nuspec file. you need to have individual nuspec accordingly to achieve this.
But if you still want to stick with same nuspec file with out renaming it or making changes to it.
i would suggest passing version at run time
nuget pack nameofnuspec.nuspec -v 1.3.4.5
-v - is version , or you can use -version as well followed by the version of your choice.
after running above command nuget package will be created with the version specified.
to check nuget package created , rename it .zip file and check ...)

Related

How to manually install packages for MikTex

I am using MikTex 2.9 and Texmaker. I need to download packages, such as the sespace package, manually from https://ctan.org/. I have done that and placed the resulting folder in: C:\Users\User1\AppData\Local\Programs\MiKTeX 2.9\tex\latex
Other previously installed packages are in that location and are recognised by MikTex as present.
The setspace folder contains setspace.sty and two test files. However when I compile in Texmaker it doesn't recognise that the package is present, and wants to download it.
Does the .sty file need to go somewhere specific, and how do I find out where that might be, please?

Add build number to package version with `dotnet pack` in VSTS Build process

With a .NET Framework library you could specify a version with a wildcard and NUGET pack command would append the build date and version automatically when running a NUGET Build Task in VSTS.
[assembly: AssemblyVersion("1.0.*")]
NUGET PACK would generate a NUPKG file with a version like 1.0.6604.1234 appending the date number and a build ID.
NET Standard issues
In .NET Core and .NET standard the new .csproj format does not support this wildcard format.
We can't package with Nuget.exe (reason: this issue) but we can use dotnet pack except I need to auto-increment the build numbers. The dotnet Build Task in VSTS allows me to wholly replace the version number, but I want to retain the version in the csproj file, and just append a build number (as I used to).
I found that using <VersionPrefix>x.y</VersionPrefix> in the csproj file would work with nuget pack and I could then add the additional parameter VersionSuffix=$(Build.BuildNumber) to the pack task.
All looked good until the first dev updated the project version in the project properties dialog. Visual Studio ignored the VersionPrefix and set the <Version> tag - and the build number fix is ignored because a Version tag exists.
Is there a way to read the Version from the csproj? If so I could set the build property to Version=$(ProjectVersion).$(Build.BuildNumber) ?
Or are there alternative ways to handle auto-incrementing the build version when packaging?
First you can select Use an environment variable for Automatic package versioning, use your defined variable such as temp ($(build.buildNumber)) as Environment variable.
More details take a look at this link: Dotnet pack automatic package versioning build number clarification
Another way is using the "arguments" field in the dotnet CLI task, you can pass additional arguments to the dotnet cli.
Using --version-suffix $(Build.BuildNumber) will pass the build
number as version suffix. Make sure you don't have a <version>
element set in your csproj, but rather a <versionprefix> element.
The built version will look like versionprefix-versionsuffix, so for
example, if you have <versionprefix>1.2.3</versionprefix> and build
number 201805002, the built version will be 1.2.3-201805002. In this case do not select the automatic package versioning.
Thanks to #patricklu-msft for his suggestions.
There is it appears no built-in way to emulate the wildcard behaviour we previously had NUGET pack with dotnet pack, nor was there way to get the <Version> tag out of the project file.
So I've created a new VSTS Build task that does this: VersionTaskReader in the MarketPlace.
This extension can be pointed to a .csproj or .vbproj and will set an environment variable VERSION, and VERSION_BUILD which has the BUILDID appended. You can optionally add a prefix to make each instance different if needed.
For example, if your project contains <Version>1.1</Version> then the VERSION_BUILD would be something like 1.1.8680
Then the dotnet pack task can use the environment variable VERSION_BUILD in the versioning options screen, so that the build number automatically increments.

How to upload an artifact to Artifactory / consume it in a build system (Gradle Maven Ant) where the artifact does not have an extension

I have the following files which I would like to upload to Artifactory as a 9.8.0 versioned artifact.
NOTE: The first two files DO NOT have an extension (they are executable files i.e. if you open them/cat on it, you'll see junk characters).
Folder/files of a given version 9.8.0 in CVS is like:
com.company.project/gigaproject/v9.8.0/linux/gigainstall
com.company.project/gigaproject/v9.8.0/solaris/gigainstall
com.company.project/gigaproject/v9.8.0/win32/gigainstall.exe
com.company.project/gigaproject/v9.8.0/gigafile.dtd
com.company.project/gigaproject/v9.8.0/gigaanotherfile.dtd
com.company.project/gigaproject/v9.8.0/giga.jar
com.company.project/gigaproject/v9.8.0/giga.war
Uploading the above files which have an extension is very easy... You log in to Artifactory as an administrator/user which has access to deploy artifacts, click on "Deploy" tab, browse for the Artifactory file and once you select the file, click on "Upload" button.
Next you'll see a screen (like shown above). You'll tweak what you want in the fields on this page and once you click on "Deploy Artifact", you are done. All you have to make sure is you select the correct file.extension file while uploading and make sure the file extension is shown in the "Target Path" box correctly (with the version -x.x.x, etc.).
My questions:
Question 1: How do I upload an artifact which doesn't have an extension? It seems like Artifactory by default takes an artifact as a .jar extension. How can I upload the "gigainstall" artifact as shown in the folder/file structure above for both Linux and Solaris? I see I can use the artifact name as gigainstall-linux and gigainstall-solaris and differentiate it, but I am not sure how to tell Artifactory that this artifact doesn't have any extension.
I don't think the development team will start generating this artifact with a proper extension (as this artifact may be hard coded everywhere in other projects where they are currently getting it from CVS/SVN source control somewhere - which is itself a bad practice to store an artifact in a source control version tool).
Question 2: How would I tell a build system (for example, Gradle) to consume a non-extensioned artifact during, let's say, 'compile' task. In build.gradle under section dependencies { .. }, I will add something like as shown below, but I am not sure for non-extensioned files (the first two in the folder/file structure I mentioned above).
dependencies {
//compile 'com.company.project:gigainstall-linux:9.8.0#'
//compile 'com.company.project:gigainstall-linux:9.8.0#??????'
//compile 'com.company.project:gigainstall-linux:9.8.0#""'
//compile 'com.company.project:gigainstall-linux:9.8.0#"none"'
//compile 'com.company.project:gigainstall-linux:9.8.0#"NULL_or_something"'
// The following will easily get giga.jar version giga-9.8.0.jar from Artifactory repository
compile 'com.company.project:giga:9.8.0'
// The following will easily get giga.war
compile 'com.company.project:giga:9.8.0#war'
// Similarly, other extension based artifacts can be fetched from Artifactory
compile 'com.company.project:gigafile:9.8.0#dtd'
compile 'com.company.project:gigaanotherfile:9.8.0#dtd'
}
Answer 1 (will cover 2 as well in a different sense): Using Artifactory "Artifact Bundle" feature section under "Deploy" tab can do the TRICK for AT LEAST uploading the artifacts in a way we want, by creating a zip file first (containing the structure and artifacts in it) --OR you can upload the artifacts using/calling Artifactory REST API way.
High level idea:
Create a zip file called gigaproject.zip OR anyname.zip/.tar/compressed file which Artifactory can read. Inside the zip, create the structure - how these artifacts will be loaded to Artifactory
i.e.
gigaproject.zip will contain the following folders/structure/files.
Case 1:
com/company/project/gigaproject/9.8.0/linux/gigainstall
com/company/project/gigaproject/9.8.0/solaris/gigainstall
com/company/project/gigaproject/9.8.0/win32/gigainstall.exe
com/company/project/gigaproject/9.8.0/gigafile.dtd
com/company/project/gigaproject/9.8.0/gigaanotherfile.dtd
com/company/project/gigaproject/9.8.0/giga.jar
com/company/project/gigaproject/9.8.0/giga.war
NOTE: In case 1 example, I didn't use any -x.x.x in the filename (i.e. I'm using plain and simple giga.jar instead of giga-9.8.0.jar).
The above Upload/Deploy will result the files (as shown in the following snapshot):
So, we have achieved what we wanted. Actually (visibly speaking yes), but not in a way Artifactory usually stores these artifacts (as they should -x.x.x version embedded in the file name and where artifact id should match the artifact filename). Now, if you want to consume the following in a Gradle build file, you CANNOT as first, you haven't uploaded the filename with -x.x.x version name in it, secondly, the artifact id in our case 1 tree was "gigaproject" (after com/company/project folder), so Gradle way of defining what artifact id and what artifact file name you want won't work.
compile 'com.company.project:gigaproject:CANNOTSAY_HOW_TO_GET_GIGA_JARorGIGAINSTALL_with_without_extension'
Conclusion: It's possible to upload any files (with/without extension in Artifactory) in any structure but it depends how your build system will consume it or will be able to consume it or not.
- I deleted the structure I just created with case 1 .zip file from Artifactory repository to try next case#2 and deleted the .zip file I created.
Case 2:
Let's create an individual versioned file name for each artifact and also create structure in the format - how Artifactory actually stores them (an artifact as seen in a repository in a tree view) and create a .zip file containing that structure. Let's use the same "Artifact Bundle" feature to upload this .zip file to upload individual artifacts that we need in Artifactory - where artifact-id (second value which we mention while trying to consume it) would match the artifactfile name in Artifactory.
Folder/file structure for the .zip file:
com/company/project/gigainstall/9.8.0/gigainstall-9.8.0.linux
com/company/project/gigainstall/9.8.0/gigainstall-9.8.0.solaris
com/company/project/gigainstall/9.8.0/gigainstall-9.8.0.exe
com/company/project/gigafile/9.8.0/gigafile-9.8.0.dtd
com/company/project/gigaanotherfile/9.8.0/gigaanotherfile-9.8.0.dtd
com/company/project/giga/9.8.0/giga-9.8.0.jar
com/company/project/giga/9.8.0/giga-9.8.0.war
NOTE: This time, we'll be using the same "Artifact Bundle" feature and for similar files (gigainstall under both Linux/Solaris folders), I took the approach of creating gigainstall folder (containing gigainstall-9.8.0.linux and gigainstall-9.8.0.solaris file names) i.e. when we'll consume these artifacts in Gradle under dependencies { ... } section for compile, we'll use x.x.x# way to fetch these artifacts from Artifactory.
OK, once "Artifact Bundle" Deploy/Upload was successfully complete, I got the following message.
Successfully deployed 7 artifacts from archive: gigaproject.zip (1 seconds).
Now, let's see how it looks like in Artifactory while searching for one of the artifact/in Tree view. You can see we have the files now in place, with filename-x.x.x.extension way so that I can consume them easily in Gradle.
In Gradle build file (build.gradle), I'll mention:
dependencies {
compile "com.company.project:gigainstall:9.8.0#linux"
compile "com.company.project:gigainstall:9.8.0#solaris"
compile "com.company.project:gigainstall:9.8.0#linux"
compile "com.company.project:giga:9.8.0
compile "com.company.project:giga:9.8.0#war
compile "com.company.project:gigafile:9.8.0#dtd
compile "com.company.project:gigaanotherfile:9.8.0#dtd
}
OH OH!! - That didn't work, see below for Gradle error. Why? - Artifactory Bundle upload/deploy feature uploads a zip file content what you have in the .zip but it DOES NOT create a .pom file per artifact it deploys. Thus, making the Gradle build to fail. May be in Ant this might succeed. This occurred for each individual .jar/.war/.dtd/etc file. I'm just showing one error example.
While doing gradle clean build
Could not resolve all dependencies for configuration ':compile'.
> Could not resolve com.company.project:gigafile:0.0.0.
Required by:
com.company.project:ABCProjectWhichConsumesGIGAProjectArtifacts:1.64.0
> Could not GET 'http://artifactoryserver:8081/artifactory/ext-snapshot-local/com/company/project/gigafile/0.0.0/gigafile-0.0.0.pom'. Received status code 409 from server: Conflict
Case 3: Let's take a simple approach (workaround but will save a lot of pain).
Create gigaproject.zip file with the following structure, this approach takes - No x.x.x version value embedded in the individual artifact/filename in the folder/file structure. We will use "Single Artifact" approach (which will create the .pom for gigaproject.zip file automatically during the upload/deploy process provided by Artifactory). You'll still be able to get gigainstall file without needing any extension to its name using this approach. During the upload/deploy step, as you already have seen, you upload gigaproject.zip and artifactory will upload it to a given Target Repository as "gigaproject-x.x.x.zip" where x.x.x is 9.8.0 in our case. See the image snapshot below.
gigaproject/linux/gigainstall
gigaproject/solaris/gigainstall
gigaproject/win32/gigainstall.exe
gigaproject/gigafile.dtd
gigaproject/gigaanotherfile.dtd
gigaproject/gigaproject.zip
gigaproject/giga.jar
gigaproject/giga.war
Now, upload it in Artifactory using "Single Artifact" feature. Click "Deploy Artifact" once you tweak the values for GroupId, ArtifactId, Version, etc.
Once this is uploaded. You'll see in the zip artifact in the target repository (I took a bad example, usually this would be libs-snapshot-local or libs-release-local instead of ext-...), you'll be able to consume the ZIP artifact directly in Graddle:
dependencies {
// This is the only line we need now.
compile "com.company.project:gigaproject:9.8.0#zip"
}
Once the .zip is available to Gradle build system, now you can tell Gradle to unpack this .zip file somewhere in your build/workspace area where you can feed the actual(unpacked) files (gigainstall, .dtd, .jar, .war, etc.) to the build process/steps.
PS: Case# 1 and 2 would have worked for Ant I guess.
Answer 2:
If you have uploaded a non-extensioned file in either way. Make sure you have manually created/uploaded its POM file as well (i.e. if I uploaded gigainstall-9.8.0 as an artifact under com/company/project/gigainstall/9.8.0/gigainstall-9.8.0, then at the same level, I have to/should create it's POM file (see a simple template .pom file for a custom jar artifact or while uploading an extensioned file via "Single Artifact" deploy, you'll see what POM Editor window shows you) and upload both so that Gradle won't error out saying no POM conflict/error. Ant might not need pom (I didn't check that).
Once it's there in Artifactory, the following line should work -- OR comment please if you find another way.
dependencies {
// See nothing mentioned after - x.x.x#
compile "com.company.package:gigainstall:9.8.0#"
}

Why won't drjava allow me to create a jar file?

I'm making a JApplet and need to make a JAR file to connect to a .htm file with the applet tag. The simple solution I could think of was to use the tool in drjava that says "Create Jar File From Project..." but alas, it's not highlighted for some reason, so I can't do that. What I'm really looking for is either (a) an explanation as to why drjava can't turn my classes into a jar file, (b) an alternative to allow me to create this jar file, or ideally (c) both. Thanks for your help ahead of time.
I don't use Drjava, but here is how you can create a JAR file from the command line without any IDE specific complications.
Simply go to the folder/directory where your project is located. Let's say your class files are located in the bin folder. You can then use
jar cvf myapplet.jar -C bin .
The JAR is then ready to be deployed.

DocBlox error: The XSL writer was unable to find your XSLTProcessor

I am using WAMP on my local machine and I'm trying to use docblox to generate documentation for a project.
When i try to run the docblox command in my command prompt for a file that has the necessary comments, I get the error message.
C:\wamp\www\wm-ppclps>docblox run -f wm-ppclps.php -t documentation
DocBlox version 0.18.1
Starting transformation of files (this could take a while depending upon the size of your project)
ERROR: The XSL writer was unable to find your XSLTProcessor; please check if you
have installed the PHP XSL extension
I have no idea why this is error message is appearing. The command creates the documentation folder, parses the source code and it produces the structure.xml file. It just won't transform the structure into an HTML file or any other readable file.
I added the PHP install directory to my system path, I installed PEAR system wide, added PEAR install directory to my system path, installed DocBlox using the docblox pear channel, I have the necessary environment variables setup. I uncommented the php.ini line to enable the php_xsl.dll extension for WAMP and restarted WAMP. When I view the phpinfo, i see that the XSL extension is enabled (XSL version 1.1.23, compiled against libxml version 2.6.32, EXSLT enabled).
Does anyone have any idea why this is happening, has come across this problem or can point me in the right direction for an answer?
The error that you are receiving means that php does not recognize the xsl extension.
Php has got a separate ini file for CLI and web; and I presume that you have enabled the xsl extension for apache only.
You can verify this by executing php -i in your command prompt and check if the xsl extension is enabled there. If not then add your dll to the right config for your WAMP.

Resources