miércoles, 24 de febrero de 2016

Handle strong-name keys in multiproject solutions with ClickOnce

Setup Key Files
Create a password-protected private/public key pair (KeyPair.pfx) using the Visual Studio “Signing” tab within a project’s properties Extract the public key from the key pair and copy it to a separate file (Key.snk) sn.exe -p KeyPair.pfx Key.snk
Copy the KeyPair.pfx to your build server. I use C:\Program Files\MSBuild\KeyFile.pfx, because it can then be accessed by the $(MSBuildExtensionsPath) MSBuild property. Move the KeyPair.pfx file to a safe & secure location. Keep the password secret as well. Copy the Key.snk to a shared location where your developers can access it. Setup Projects for Signing
For each assembly that you want to sign:
  1. Open the Project Properties | Signing page
  2. Select the [X] Sign the assembly checkbox.
  3. Select the [X] Delay sign only checkbox.
  4. Select from the key file dropdown.
  5. Browse to the shared location and select the Key.snk file
  6. The snk file will be copied to each project directory that you assign it to
  7. Copy the key file from one of your projects into Solution Items so that you can use it for the test run configuration
Setup Test Run Configuration for Re-Signing
If you want to instrument your assemblies and enable Code Coverage for your unit tests, then you need to specify a key file for re-signing.
Open the LocalTestRun.testrunconfig file On the Code Coverage tab, select the key as the Re-Signing key file
Disable Strong-Name Verification on Developer Workstations
Since you are delay-signing with only the public key, .NET CLR assembly verification will fail with assemblies built locally. When the verification fails you won’t be able to run or debug the assemblies.
To overcome this in development, you need to disable strong-name verification for assemblies that you build locally and delay-sign with your public key.
Open a Visual Studio Command Prompt Type: sn.exe -tp Key.snk
This will output some data including the token.
Type: sn -Vr *,YOUR_KEY_TOKEN
example: sn -Vr *,0123456789abcdef
This will disable strong name verification for all assemblies signed with your public key. You can list current settings for strong name verification with: sn -Vl
Installing the Private Key for Team Build
Since the private key (Key.pfx) is password protected – Team Build cannot access it. Thanks to Nagaraju Palla’s Blog: Using Password Protected Signing Keys in Team Build , we have a solution.
Logon to the Team Build server as the build service account Open the project in Visual Studio Build the project in Visual Studio You will be prompted for the password to the private key file. Enter the password Close Visual Studio & Log off The private key file is now installed in the build service account’s local certificate store and Team Build can access it without prompting for the password again. This certificate store is as secure as the build service account’s password. (Hint: Make it just as strong as your keyfile’s password)
Updating TFSBuild.proj Build Script
Team Build has access to the private keyfile and password. This allows it to fully-sign the assemblies.
To override the project settings and instruct Team Build to use the private keyfile and disable partial-signing, we need to set the CustomPropertiesForBuild property in TFSBuild.proj
Check-out your TFSBuild.proj build script Search for the placeholder property (near line 130 by default) Replace it with the following: SignAssembly=true;DelaySign=false;AssemblyOriginatorKeyFile=$(MSBuildExtensionsPath)\Key.pfx Check-in your changes Queue a build Verifying Team Build output
To check that Team Build has correctly strongly named your assemblies, you can use the sn.exe utility to verify the strong name signature.
Open a Visual Studio Command Prompt Type: sn.exe -vf assemblyname.dll
You can also verify all your assemblies at the same time:
Open a Visual Studio Command Prompt Type: FOR %a IN (*.dll) DO sn.exe -vf %a

jueves, 20 de noviembre de 2014

SqlServer Management Tools + Warning about Saving changes is not permitted

The Save (Not Permitted) dialog box warns you that saving changes is not permitted because the changes you have made require the listed tables to be dropped and re-created.
The following actions might require a table to be re-created:
  • Adding a new column to the middle of the table
  • Dropping a column
  • Changing column nullability
  • Changing the order of the columns
  • Changing the data type of a column
To change this option, on the Tools menu, click Options, expand Designers, and then click Table and Database Designers. Select or clear the Prevent saving changes that require the table to be re-created check box.

martes, 30 de septiembre de 2014

TFS: El build no termina nunca, corre por siempre

Alguna vez me pasó que el build llevaba un día entero colgado en la parte del publish de ClickOnce. 
Lo que sucedió es que por algún motivo una ventana de dialogo (pop-up) se abrio y quedo esperando (por siempre) a que alguien la cierre.
Me dí cuenta al loguearme al build server con la cuenta que corre el build. Otra forma de darse cuenta es checkeando el event log por errores/warnings.
Como es ClickOnce, lo que pudo ocurrir es que el certificado digital que necesitaba usar para firmar los manifiestos se halla importado/instalado con la opción de preguntar por la contraseña (primera opción). Simplemente hay que desinstalarlo y volverlo a importar como sugiere esta imagen:


miércoles, 3 de septiembre de 2014

Firmar assemblies y manifiestos de ClickOnce con Strong Name Keys

1. ¿Qué es un certificado digital?

Es una herramienta que se usa para verificar la integridad de los datos que se transmiten entre el origen (quien firma) y el destinatario (quien verifica). Los certificados o firmas digitales son creadas y verificadas utilizando criptografía de llave pública. Quien firma posee una un par de llaves criptográficas: una llave publica, que es usada para verificar que el firmante conoce la clave privada y el mensaje.

En algunos casos (como el que estamos viendo aquí), con ayuda de más infraestructura, podemos usar los certificados para saber y corroborar el nombre del que firma los mensajes, y asegurarnos además que el mensaje no ha sido alterado luego de que el firmante creara la firma para ese mensaje. Entre todos los mecanismos que existen para implementar las firmas digitales, Microsoft .NET utiliza para sus Strong Name el algoritmo RSA de clave publica y el algoritmo hash SHA-1.

Hay certificados de prueba y hay certificados reales firmados por autoridades de certificación (CAs) como por ejemplo Verisign. También se puede crear un certificado de prueba y luego hacerlo firmar por un CA.

2. ¿Qué es un Strong Name?

Es un mecanismo de Microsoft .Net para darle a nuestros assemblies una identidad única. La identidad está compuesta por:
* una clave pública (RSA)
* un nombre (texto del nombre del archivo - sin extensión - que contiene el assembly)
* versión (compuesta por cuatro partes: Major.Minor.Build.Revision. Ej: 10.0.0.1)
* certificado digital (contiene la clave privada)
* cultura (opcional)
* arquitectura del procesador (opcional)

Para obtener un Strong Name válido, nuestro assembly es firmado (strong-name signed) durante el proceso de build usando la clave privada que corresponde a la clave publica en el Strong Name. De esta forma la firma Strong Name puede ser verificada con la clave pública. Hay varias técnicas distintas para crear una firma Strong Name y para manejar la clave privada durante el firmado que explicaré más adelante.

Cuando un assembly hace referencia a un strong-named assembly, captura la información del strong name del assembly referenciado. Cuando el framework de .net intenta cargar un strong-named assembly, verifica la firma strong-name, si no lo puede hacer, entonces directamente no lo carga.

Una excepción a este proceso se da con strong-named assemblies que están en el Global Assembly Caché (GAC). Estos assemblies no son verificados cada vez que .Net los carga porque ya fueron verificados cuando se instalaron en el GAC. El GAC es un repositorio restringido con solo acceso a Administradores, con lo cual si ya fueron ingresados se entiende que ya es suficiente con haberlos validado en ese momento.

3. ¿Cuando deberíamos firmar con Strong Name keys nuestros assemblies?

Cuando necesitemos que nuestros componentes (dlls) tengan una identidad única (que nadie los pueda falsificar) y garantizar que nuestras dependencias se mapean correctamente con las versiones correctas.

El tema de falsificar la identidad del assembly tiene que ver con que alguien obtenga la clave privada (que deberíamos mantener.. privada!) y firme cualquier otro assembly o el mismo modificado con nuestra strong-name key y se haga pasar por nosotros. Tener un strong-name nos permite tomar ciertas decisiones respecto a seguridad como confiar en todos los assemblies firmados con nuestro strong-name dentro de nuestra intranet. Digo intranet porque una firma strong-name no nos asegura nada respecto del que firma (publisher), con lo cual no podriamos confiar en un strong-name de un assembly externo o de internet (salvo que tengamos un canal seguro desde donde obtener la clave pública de ese assembly, o sea, un CA!).

Típicamente firmamos DLLs, no EXEs. Firmar un EXE implica que no podrá referenciar DLLs que no esten firmadas con strong-name, y esto complica las cosas. En vez de esto se firman los manifiestos del EXE que apuntan a las DLLs que no están firmadas. Lo mismo sucede con DLLs firmadas con strong-name que referencian a otras DLLs que no están firmadas (ya sea nuestras o peor, de terceros), esto es un problema porque sí o sí todas las DLLs deberán estar firmadas con strong-name, sino no compilará nuestro proyecto.

Por otro lado tener los assemblies firmados complica el deployment. Por ejemplo si necesitamos hacer un bug fix en uno de nuestros assemblies, incrementando el numero de versión para ese assembly, provocará que la aplicación luego no encuentre el assembly (buscará el anterior). Para solucionar esto deberemos compilar la solución completa para ese assembly, peor aún si es un assembly compartido entre varias aplicaciones. Una alternativa en el caso que el assembly esté en el GAC sería usar las publisher policy para redirecionar el cargado de la version 1.0.0.0 a la version 1.0.0.1 (la del bug fix), pero esto sería complicar aún más las cosas. Finalmente podríamos no cambiar el numero de versión y la aplicación encontraría el assembly.

Como ven, firmar con strong-name añade complejidades y deberíamos evitar firmar con strong-name nuestros assemblies salvo que vayan a ser instalados en el Global Assembly Cache (GAC) o salvo que vayan a ser recursos compartidos (DLL) de otras aplicaciones. Firmarlos porque sí solo agrega más esfuerzo y problemas.

Para más detalle ver: Strong-Name Signing for Managed Applications.
http://msdn.microsoft.com/en-us/library/xwb8f617(v=vs.110).aspx#bypassing_signature_verification

4. ¿Qué es un certificado .pfx?

Significa Personal Information Exchange y es una strong name key (.snk) protegida por contraseña.

5. ¿Cuando deberíamos firmar los manifiestos de ClickOnce?

En ClickOnce, debemos firmar obligatoriamente los manifiestos. Esto se hace utilizando un archivo .pfx o un certificado de nuestro personal certificate store.

Si usamos el archivo .pfx debermos ingresar la contraseña del mismo para que pueda ser importado al personal certificate store.

6. ¿Como se firman las librerías y manifiestos de ClickOnce de nuestros proyectos a través de Visual Studio?

En las propiedades del proyecto que queremos firmar, si vamos a la solapa "Signing" encontraremos la página de configuración para firmar el proyecto. Ésta tiene dos secciones: Sign the ClickOnce manifests y Sign the assembly.
Referencias:

  • Using Strong Name Signatures: http://msdn.microsoft.com/en-us/magazine/cc163583.aspx#S8
  • http://msdn.microsoft.com/es-ar/library/aa730868(v=vs.80).aspx


martes, 17 de junio de 2014

KANBAN vs SCRUM

Quería compartir con  ustedes una breve comparación entre dos metodologías que están de moda estos últimos años. Ambas son ágiles, pero existen fundamentalistas de ambos lados, que dice que una es mejor que la otra. Entonces, ¿Cuál se adecuará mejor a tus proyectos? ¿Cuál es la tendencia mundial?

Antes que nada voy a hacer un breve repaso de ambas, para luego revisar las similitudes y diferencias para que podamos entender cuál es la mejor metodología:

Scrum en pocas palabras

  • Divide tu organización en equipos pequeños, multidisciplinarios y auto-organizados.  
  • Divide  el  trabajo  en  una  lista  de  entregables  pequeños  y concretos.  Ordena  la  lista  por  orden  de  prioridad  y  estima  el esfuerzo relativo de cada elemento. 
  • Divide  el  tiempo  en  iteraciones  cortas  de  longitud  fija (entre 1  y  4  semanas),  con  código  potencialmente entregable y demostrado después de cada iteración. 
  • Optimiza  el  plan  de  entregas  y  actualiza  las  prioridades  en colaboración  con  el  cliente,  basada  en  los  conocimientos adquiridos  mediante  la  inspección  del  entregable  después  de cada iteración.
  • Optimiza  el  proceso  teniendo  una  retrospectiva  después  de cada iteración.


 Así  en  lugar  de  un  grupo  numeroso  pasando  mucho  tiempo construyendo  algo  grande,  tenemos  un  equipo  menor  pasando  un tiempo  más  corto  construyendo  algo  menor.  Pero  integrando  con regularidad para ver el conjunto.

Kanban en pocas palabras

  • Visualiza el flujo de trabajo
    • Divide  el  trabajo  en  bloques,  escribe  cada elemento en una tarjeta y ponlo en el muro.
    • Utiliza columnas con nombre para ilustrar dónde está cada elemento en el flujo de trabajo.
  • Limita  el  WIP  (Work  in  Progress,  trabajo  en  curso)  - asigna  límites  concretos  a  cuántos  elementos  pueden  estar  en progreso en cada estado del flujo de trabajo.
  • Mide  el  lead  time  (tiempo  medio  para  completar  un elemento, "tiempo  de  ciclo"),  optimiza  el proceso  para  que  el  lead  time  sea  tan  pequeño  y  predecible como sea posible.


Kanban deja casi todo abierto. Las únicas normas son Visualiza tu Flujo de  trabajo  y  Limita  tu  WIP  (Work  In  Progress,  Trabajo  en  curso).  

¿En qué se parecen?

  • Ambos son Lean y Ágiles:
    • Tanto  Scrum  como  Kanban  son  sistemas  de  planificación  tipo "Pull", principio de gestión de inventario 'Just In Time' (JIT) propio de Lean. Esto significa que el equipo elige cuándo y cuánto trabajo acometer.  Ellos  (los  componentes  del  equipo)  "tiran"  del  trabajo cuando  están  listos,  en  contraposición  a  que  desde  el  exterior  se "empuje" al equipo a hacerlo. Al igual que una impresora tira de la siguiente página solo cuando esta lista para imprimir en ella (aunque tenga hojas de papel en la bandeja).
    • Scrum y Kanban se basan en procesos de optimización continuos y empíricos, que se corresponden con el principio Kaizen de Lean.
    • Scrum y Kanban dan más importancia a la respuesta al cambio que  al  seguimiento  de  un  plan  (aunque  Kanban  permite, típicamente,  una  respuesta  más  rápida  que  Scrum).  Uno  de  los cuatro principios del manifiesto ágil.  
  • Ambos establecen límites WIP, Kanban lo limita por flujo de trabajo, Scrum por iteración (capacity).
  • En ambos la visibilidad del proceso es la base de su mejora.
  • Ambos tienen como objetivo la entrega temprana y frecuente de software.
  • Ambos trabajan con equipos auto-organizados.
  • Ambos necesitan la división del trabajo en partes.
  • Ambos revisan y mejoran de forma continua el plan del producto en base a datos empíricos (velocidad / tiempo de entrega)

¿En qué se diferencian?

 Scrum
 Kanban
 Iteraciones de tiempo fijo.
Sin iteraciones. La cadencia puede variar en funcion del plan de negocio y la mejora del proceso.
 La métrica principal es la Velocidad (story points "done" por sprint).
 La métrica principal es el Lead Time (tiempo medio que tarda una petición en salir del ciclo).
 Equipos multifuncionales.
 Sin restricciones, pueden ser multifuncionales o especializados.
 El tamaño de las tareas no puede exceder la duración del sprint.
 Sin restricciones, aunque se recomienda que todas sean de la misma longitud para tener mas previsibilidad.
 Se utiliza el Burndown Chart como diagrama de seguimiento diario
 No prescribe ninguno, aunque se recomienda el de Cumulative Flow Chart.
 Se emplea una limitacion WIP indirecta (por sprint).
 Se emplea una limitación WIP directa (por el estado del trabajo).
 Se deben realizar estimaciones
 Las estimaciones son opcionales.
 No se pueden añadir tareas directamente en medio de una iteración. Hay que negociar con el dueño del Producto y el Equipo que se quita si se añade más trabajo. En general no está recomendado.
 Siempre que haya capacidad disponible, se pueden añadir tareas.
El Backlog del sprint pertenece a un equipo determinado.
Varios equipos  pueden compartir la misma pizarra Kanban.
 Se prescriben 3 roles (Product Owner, Scrum Master y Equipo).
 No hay roles. Se pueden tener todos los roles que se considere necesario.
 En cada sprint se limpia el sprint backlog.
 El tablero de Kanban es persistente.
 El Product Backlog debe estar priorizado.
 La priorización es opcional, generalmente se priorizan los elementos próximos a desarrollarse.

¿Cuál es el mejor?

Todo depende del contexto en que lo uses. Por ejemplo, Scrum es lo ideal si se dan estas condiciones:

  1. Posibilidad de tener una persona con suficiente tiempo de dedicación al rol de Product Owner (que tenga tiempo de tomar los requerimientos del cliente y escribir las historias de usuario; estar 100% disponible para el equipo de desarrollo; tiempo para mantener un Product Backlog priorizado y con suficientes historias de usuario detalladas para un sprint de trabajo; etc).
  2. Scrum Master con disponibilidad 100% para el equipo, facilitando el trabajo de todos y quitando los impedimentos a tiempo.
  3. Cantidad de trabajo suficiente de parte del cliente como para cubrir un sprint y que no queden tiempos muertos entre sprint y sprint.
  4. Equipo de trabajo lo más auto-suficiente y auto-organizado posible, sin diferencias técnicas notables.
  5. Los requerimientos son cambiantes, pero el cliente está más dispuesto a postponer el cambio a la siguiente iteración.
  6. Estamos desarrollando un nuevo producto, lo cual implica un mínimos de trabajo suficiente para 3 meses y una mínima planificación de prioridades.
En cambio Kanban es más adecuado si por ejemplo:
  1. La cantidad de trabajo de parte del cliente es muy fluctuante (a veces mucho, a veces no alcanza a la semana continua de trabajo) o la persona encargada de tomar los requerimientos al cliente (el PO en Scrum) tiene también otras asignaciones y su cadencia para llevar las peticiones al equipo de desarrollo es fluctuante.
  2. El equipo de trabajo es demasiado especializado o con diferencias técnicas notables, donde se hace muy difícil la estimación del trabajo a realizar.
  3. Los requerimientos son muy cambiantes o estamos en una fase de mantenimiento, donde el cambio debe llegar lo antes posible a producción y no podemos esperar a que termine un sprint.
  4. Llevas múltiples productos al mismo tiempo. Kanban no discrimina entre productos, sino tareas en un flujo de trabajo.
Scrum es más restrictivo que  Kanban  ya  que  prescribe  cosas  como  iteraciones  y  equipos interdisciplinarios. Kanban está más cerca del "hace lo que quieras", si bien esto parece muy ágil, hay que tener en cuenta que la falta de límites también dificulta la gestión.


Si  haces  iteraciones  cada  vez  más  cortas, esencialmente te estás aproximando a Kanban. Una vez que se empieza a  hablar  de  hacer  durar  la  iteración  menos  de  una  semana,  se  debería considerar abandonar definitivamente las iteraciones a tiempo cerrado.

En cuanto a las reuniones diarias y las retrospectivas, recomiendo tenerlas en ambas metodologías.


¿Cuál es la tendencia?

Hasta el 2013, Scrum y sus variaciones (73%) siguen siendo las metodologías ágiles más populares. Kanban representa sólo el 5% aunque viene creciendo lentamente.


Final

Este tema da para hablar muchísimo más de lo que he puesto acá, si tenés alguna duda o algo para agregar no dudes en comentarlo. Tienes algún ejemplo o anécdota que quieras compartir?


Referencias

http://www.crisp.se/file-uploads/Kanban-vs-Scrum.pdf
http://www.versionone.com/pdf/2013-state-of-agile-survey.pdf


viernes, 22 de noviembre de 2013

Cannot import the following key file: [xxxxxxxxx].pfx

Muchas veces cuando intentamos correr un proyecto con librerías firmadas el Visual Studio nos da este error:

Error  9       Cannot import the following key file: [xxxxxxxxx].pfx. The key file may be password protected. To correct this, try to import the certificate again or manually install the certificate to the Strong Name CSP with the following key container name: VS_KEY_xxxxxxxxxxxx  [ProjectName]
Para solucionar esto debemos instalar el certificado en el key container que nos especifica. Para ello debemos abrir una consola de comandos de desarrollador (developer command prompt) en modo administrador, movernos hasta la carpeta donde esta el archivo pfx y escribir el siguiente comando:
sn -i <[xxxxxxxxx].pfx> <VS_KEY_xxxxxxxxxxxx>
El resultado debería ser que nos instaló correctamente el certificado. Luego solo debemos hacer doble click en el archivo del certificado e instalarlo. 
Si el certificado fue añadido anteriormente debemos borrarlo e intentarlo de nuevo. Para ver los certificados instalados y poder borrarlos correr el comando certmgr.exe
Para poder borrar un contenedor corremos el comando sn -d <VS_KEY_xxxxxxxxxxxx>

viernes, 14 de junio de 2013

ClickOnce: There was an error during installation + file:///xxx.vsto did not succeed.

Error al instalar add-in de excel con ClickOnce:



Introducción:

Tenemos un add-in para excel el cual se instala con clickonce. El instalador está publicado en internet, con lo cual el usuario se baja el setup.exe, el cual a su vez determina si debe bajarse el resto de los archivos si es que se instala por primera vez o no.

Problema:

El error es que intenta buscar el archivo .vsto en el mismo lugar donde esta el setup.exe, cuando en realidad debería bajarlo de la URL de instalación.

Nuestro proyecto está manejado por Team Foundation Server y tenemos automatizado el proceso de publicación (publish) desde el TFS, con lo cual con cada check-in se dispara un publish. Para ello tenemos dos campos personalizados donde ponemos el Publish Directory (donde iran los archivos del instalador) y el Publish URL (url publica donde se podrá descargar el instalador). Nuestro proceso reemplaza los path configurados en el archivo de proyecto con los path configurados en los campos personalizados del build template.

El problema se daba que al no poner nada en el proyecto para el publish URL, nuestro proceso no tenía un string para reemplazar y por lo tanto ese string quedaba vacío, entonces clickonce cuando buscaba los archivos complementarios al instalador, al no tener publish url, lo hacía en el mismo directorio desde donde se corría el TFS.

Solución:

La solución fue poner cualquier URL en el PublishURL del proyecto para que nuestro proceso de build tuviera con que reemplazar.