Проекты из разных Solution-ов, Nuget и hint path

193
21 апреля 2017, 17:51

Дано: Есть 2 солюшна.

  1. MVC приложение
  2. Набор библиотек с бизнес-логикой

Для дебага мне приходится добавлять нужные проекты в один солюшн. Я просто добавляю нужные проекты с бизнес логикой из солюшна 2 в мой солюшн 1 с моим MVC приложением.

Проблема: Проблема в hint path и packages. Дело в том что когда ты выкачиваешь Nuget Packages для проекта, то он кладет их в папку packages около солюшена в рамках которого ты это делал.

Когда я добавляю проект из солюшна 2 в солюшн 1, а потом обновляю/добавляю какие-то Nuget packages, то они скачиваются в папку packages для солюшна 1. В то время как проект из солюшна 2 имеет hint path типа "../packages...". То есть он смотрит на папку packages своего, 2-го, солюшна. Естественно приходится менять hint path чтобы они смотрели на папку packages не от 2 солюшна.

Почему это проблема: Потому что check-in-ить такие hint path нельзя. И в случае, когда csproj файл изменился (добавились например какие-то файлы), то приходится чистишь csproj файл. Писать правильные hint path оставляя при этом другие изменения, check-in-ить, а потом возвращать нужные hint path.

Вопрос: Как избежать этих танцев с hint path и при этом оставить возможность девелопить и билдить проект в рамках разных солюшнов?

Уточнение: Каждая библиотека с бизнес-логикой лежит в нугете. И при обычном сцении работы я её подключаю как нугет. Без этих танцев с добавлением проекта к солюшну. НО. Когда возникает ситуация когда мне нужно изменить эту бизнес логику и сразу же её подебажить в рамках конкретного приложения, то тогда мне приходится уже брать исходники этого нугета и добавлять в солюшн с моим приложением. Но мой вопрос вовсе не про это.

Мой вопрос про то, что у этой библиотеки с бизнес-логикой, которую я добавляю в свой солюшн для дебага, есть зависимости на другие нугеты. И эти нугеты нужно заресторить чтобы всё скомпилить. Но проблема в том что рестор кладет все библиотеки в package папку около солюшна в рамках которого мы это делаем.

А проект с бизнес логикой, который я добавляю в свой солюшн, физически хранится в другом месте, и состоит в рамках другого солюшна. И hint path в csproj смотрят на папку packages для его солюшна, а не для того в который я его добавляю. Вот тут проблема.

Зачекинить я эти hint path'ы, которые изменены чтобы смотреть на папку packages другого солюшна, не могу. Потому что тогда билд сломается на билд сервере.

Да, я могу держать открытым солюшн в котором состоит нугет с бизнес логикой, чтобы там делать нугет-рестор. Но хочется избавиться от этого и работать в рамках одной студии.

Answer 1

Мы вынесли общий код в Nuget-пакеты. Используем TFS Online, где можно создать своё хранилище пакетов. Это хранилище подключается в Visual Studio к обоим проектам.

Всё, что нужно было узнали из документации Microsoft.

Практические советы:

  1. Для Nuget'ов завели отдельный репозиторий в TFS Online.
  2. Все Nuget'ы держим в одном солюшене, хотя это не обязательно. Просто у нас над ними работает только она команда, а если будут разные, можно и разнести.
  3. nuget.exe держим прямо в солюшене из пункта 2.
  4. Используем самописный скрипт на PowerShell, чтобы увеличивать номер версии пакета перед сборкой и публиковать. Выглядит так:

    param($csproj, $version)
    if ($version -ne 'major' -and $version -ne 'minor' -and $version -ne 'revision') {
      Write-Host 'Usage: build-next-version <.csproj file> major|minor|revision'
      exit -1
    }
    $csprojPath = Resolve-Path $csproj |
                  Split-Path
    $assemblyInfo = Join-Path -Path $csprojPath -ChildPath "Properties/AssemblyInfo.cs"
    Write-Host "AssemblyInfo.cs: $assemblyInfo"
    $versionPattern = "AssemblyVersion\(""(\d+)\.(\d+)\.(\d+)\.0""\)"
    $assemblyInfoVersion = Select-String -Path $assemblyInfo -Pattern $versionPattern -List
    $matches = $assemblyInfoVersion.Matches
    if (-not $matches.Success) {
      Write-Host "Can't find [assembly: AssemblyVersion(""M.m.r.0"")]"
      exit -2
    }
    $major = [Convert]::ToInt32($matches.Groups[1], 10)
    $minor = [Convert]::ToInt32($matches.Groups[2], 10)
    $revision = [Convert]::ToInt32($matches.Groups[3], 10)
    Write-Host "Detected version: $major.$minor.$revision"
    if ($version -eq 'revision') {
      $revision++;
    }
    elseif ($version -eq 'minor') {
      $revision = 0;
      $minor++;
    }
    elseif ($version -eq 'major') {
      $revision = 0;
      $minor = 0;
      $major++;
    }
    $newVersion = "$major.$minor.$revision"
    Write-Host "New version: $newVersion"
    (Get-Content $assemblyInfo) |
      % { $_ -replace "(Assembly(File)?Version)\(""([^""]+)""\)", "`$1(""$newVersion.0"")" } |
      Set-Content $assemblyInfo
    $nugetPath = $csproj -replace '\.csproj$', ".$newVersion.nupkg"
    Write-Host "NuGet packet: $nugetPath"
    $nuget = Split-Path -Parent $MyInvocation.MyCommand.Path | Join-Path -ChildPath NuGet\nuget.exe
    & 'C:\Program Files (x86)\MSBuild\14.0\Bin\MSBuild.exe' $csproj /p:Configuration=Release
    & $nuget pack $csproj  -Properties Configuration=Release -OutputDirectory $csprojPath
    & $nuget push $nugetPath -Source <Здесь вставить ULR хранилища, что-то вроде https://company.pkgs.visualstudio.com/_packaging/ProjectName/nuget/v3/index.json> -ApiKey VSTS
READ ALSO
Canvas, как панель для набора элементов, и Behaviors

Canvas, как панель для набора элементов, и Behaviors

Мне нужно в качестве панели для элементов указать Canvas и подключить возможность перемещать элементы в ней

247
Как прицепиться к окну?

Как прицепиться к окну?

Можно ли как то привязать окно моей программы к окну другой программы?

199
Удалить из списка значения, которых нет в другом списке

Удалить из списка значения, которых нет в другом списке

Для того, чтобы удалить все элементы подходящие под условие можно использовать метод RemoveAll

236
Повторный вызов метода OnCreate()

Повторный вызов метода OnCreate()

При развертывании проекта (чтение sms-сообщений), после получения сообщения приложение открывается три разаПо-моему OnCreate() запускается несколько...

222