Eu estou tentando pegar instantâneos do meu próprio site usando phantomjs - basicamente, isso é para criar uma imagem de visualização do conteúdo enviado pelo usuário. Eu instalei phantomjs no servidor e confirmei que executá-lo a partir da linha de comando contra as páginas apropriadas funciona bem. No entanto, quando tento executá-lo no site, ele não parece fazer nada. Confirmei que o código está sendo chamado, que o fantasma está realmente em execução (eu monitorei os processos e posso vê-lo aparecer na lista de processos quando o chamo) - no entanto, nenhuma imagem está sendo gerada. Não tenho certeza onde eu deveria estar olhando para descobrir por que ele não vai criar as imagens - quaisquer sugestões O bloco de código relevante está abaixo: perguntou Estou usando o grunhido (javascript Task runner) para o meu processo de desenvolvimento de desenvolvimento web. Incluem-se coisas como testes com jasmine, verificação de código com plato, documentação (YUIdoc) e assim por diante. Para tornar as coisas um pouco mais convenientes (e também incluir esse processo de construção em outro processo de construção posteriormente), tentei criar um aplicativo. net (C) simples, capaz de executar os comandos grunt e, em seguida, gerar os resultados em uma caixa de texto. Como eu sempre posso executar os comandos do grunhido facilmente através do cmd-Window eu tentei utilizar o System. Diagnostics. Process com o cmd. exe para fazer isso. Aqui está o que eu tentei (para gerar a documentação do código): Primeira coisa que é esquisita: Estou recebendo esta saída: Sim, eu uso require. js dentro do meu projeto, mas isso não tem nada a ver com documentação. Esta é a saída que normalmente recebo e esperava: E a documentação não é gerada, é claro. Mas existe um arquivo data. json que é gerado na pasta correta, mas está vazio. Assim, pelo menos parece que começou corretamente, mas não pôde continuar () Eu também tentei com outras tarefas, mas nenhum deles funciona usando um processo em C. perguntou 13 de agosto 14 em 15: 41 Assim que um projeto de desenvolvimento de software requer mais de um Um único desenvolvedor, um conjunto de novos problemas e preocupações são introduzidos à medida que os membros da equipe começam a colaborar. Coisas como os métodos de comunicação a serem usados, como compartilhar o progresso e como minimizar os conflitos. As equipes geralmente são capazes de trabalhar com essas preocupações e chegar a formas preferidas de trabalhar sem nenhuma contribuição externa, se elas forem autônomas e se sentirem empoderadas, isto é, se permitirem se auto-organizar. Muitas vezes tenho visto membros da equipe que têm medo de tomar decisões por si mesmos, pois não é o trabalho deles, isso é para os gerentes. Infelizmente para a nossa indústria, a administração tem sido muitas vezes equiparada à direção. Os gerentes que atribuem trabalho são a incorporação clássica dessa mentalidade. A maioria das pessoas não gosta que lhes digam o que fazer, particularmente quando sabem que está errado, e os gerentes que atribuem tarefas com base em seus próprios preconceitos geralmente produzem o resultado errado. Além disso, quando os gerentes são responsáveis por acompanhar o trabalho e cumprir os prazos, muitos acham difícil resistir ao microgerenciamento, e isso é um problema, já que o microgerenciamento é um dreno moral. Eu sempre disse o seguinte quando os gerentes tentaram me microgerenciar (provavelmente menos diretamente): Eu sei o que estou fazendo e como fazê-lo. Se eu precisar de ajuda, vou encontrá-lo ou me tornar conhecido. Agora, algumas pessoas precisam de ajuda para desenvolver a iniciativa e chegar a um ponto em que estejam dispostas a se dar a conhecer ou a identificar quando devem fazê-lo. Parte disso se deve à má gestão, em primeiro lugar, que quando as pessoas se tornam conhecidas, elas são microgerenciadas ou não são suficientemente apoiadas (leia-se desmascarado), então elas ficam quietas, exacerbando o problema. É uma responsabilidade compartilhada da equipe e da gerência manter a eficácia das equipes, de forma que ambas ajudem os indivíduos a desenvolver essas habilidades. Wikipedia define gestão como: o ato de reunir as pessoas para alcançar metas e objetivos desejados usando recursos disponíveis de forma eficiente e eficaz Na minha opinião, gerenciamento de software é sobre a definição das metas e objetivos, se eles não são definidos e apoiar a equipe. Trata-se principalmente de garantir que exista um ambiente onde eles possam trabalhar de forma eficiente e remover tudo o que estiver em seu caminho. O que fica no caminho deles pode ser qualquer coisa, desde o ar-condicionado sendo muito frio até a remoção de pessoas problemáticas da equipe, mas certamente não deve ser o gerente que atrapalha (como seria o caso se eles insistissem em fazer cada decisão). Os métodos ágeis cresceram em aceitação tão rapidamente, em parte porque permitem que os desenvolvedores retrocedam contra práticas ruins de gerenciamento que sufocam a produtividade. Curiosamente, eles também tendem a resultar em projetos mais gerenciáveis com melhores resultados. Talvez o maior benefício que os métodos ágeis obtenham seja ajudar a reduzir o impacto do mau gerenciamento. Nos últimos projetos em que trabalhei, a necessidade de testes de JavaScript cresceu à medida que o comportamento do cliente aumentou. Melhorias recentes em componentes e bibliotecas JavaScript tornaram mais fácil mover mais comportamento de exibição para o cliente e criar interfaces de usuário mais ricas e mais responsivas. Para escrever testes para cobrir esse código, avaliei as estruturas de teste QUnit e Jasmine. O Jasmine combinava melhor com o modo BDD que eu queria estruturar meus testes (particularmente aninhando testes em especificações e subespecificações). Atualmente, executamos todos os testes de unidade e integração como parte do processo de criação do TeamCity, mas como integramos testes JavaScript, que idealmente precisam ser executados em uma instância de um ou mais navegadores de destino. A solução é razoavelmente direta, mas com uma limitação (que Espero que seja temporário). Digite JsTestDriver. Este incrível projeto nos permite carregar e executar arquivos JavaScript em um navegador que é capturado pelo processo do servidor. Detalhes completos de como isso é feito podem ser encontrados no site do projeto. Basicamente, para um CI, esse processo de navegador e servidor capturado existe em um servidor remoto. A limitação é que isso precisa ser uma sessão interativa e, atualmente, só consegui fazer isso funcionar na minha sessão, que deixo ativo e que causa muitas falhas quando os servidores são reiniciados acidentalmente. Um problema para outro dia. Uma vez que este servidor remoto está configurado, é realmente apenas uma questão de configurar o arquivo de configuração yaml (jsTestDriver. conf aqui): E executando algo como o seguinte script: O valor do servidor é o ponto final configurado no servidor remoto. Os valores de carga são os arquivos javascript que serão carregados e executados. O jasmine. js é o arquivo do framework Jasmine e o JasmineAdapter. js é um excelente adaptador JsTestDriver para suportar o Jasmine. Uma vez que estes são carregados, qualquer teste de Jasmine em arquivos subseqüentes será executado. No exemplo acima, fileundertest. js contém o código que queremos testar e fileundertest. specs. js contém os testes do Jasmine. Obviamente, você pode adicionar quantos arquivos forem necessários e até mesmo incluir dependências como jQuery, embora isso comece a ficar um pouco rude. Existe um plugin Jasmine que suporta manipulação de jQuery e DOM para o leitor interessado. Os resultados são enviados para OutJsTestDriverResults em um formato compatível com JUnit, que pode ser lido pelo TeamCity quando esse script é executado como parte de uma compilação. Estes resultados, em seguida, aparecem no TeamCity e qualquer teste com falha será fácil de detectar. Disclaimer: Estes resultados são baseados em mim brincando com o MongoDB. Eu tenho muito pouca experiência / compreensão, então não assuma nada abaixo como a verdade. Como todos sabemos, YMMV. Estamos pensando em usar o MongoDB no trabalho para compartilhar o estado entre os membros do nosso sistema. Uma das razões pelas quais gosto é que é (recentemente) simples criar conjuntos de réplicas para fornecer redundância. No entanto, se você quiser garantir que as alterações tenham sido replicadas para um quorum de máquinas ou, de fato, verificar se uma gravação chegou a qualquer servidor MongoDB, será necessário chamar getLastError. Tudo isto é tratado de forma transparente nos drivers do MongoDB por SafeMode. Isso é bom, mas precisamos entender o impacto no desempenho que a retenção implica na replicação, já que nosso aplicativo ficará bloqueado enquanto estiver ocorrendo. Eu configurei um ambiente de teste virtual para isso (eu mesmo configurar um controlador de domínio, mas isso é outra história). Instalei o MongoDB em dois servidores e configurei-os para fazer parte do mesmo conjunto de réplicas. Meu programa de teste usou o driver oficial e inseriu 1000 registros de pessoa em uma coleção. A coleção foi descartada antes de cada modo ser testado. Os números dos testes foram consistentes, independentemente da ordem dos modos. Eu testei 5 modos: nenhuma chamada para getLastError (não podemos verificar a gravação foi recebida) Isso mostra claramente que há um preço alto a pagar por aguardar a replicação. Garantir que a gravação foi gravada em disco é muito mais barata e pode ser suficiente para nossos propósitos. Esses testes estavam sendo executados em máquinas virtuais hospedadas em minha estação de trabalho, por isso seria interessante ver os resultados em servidores dedicados. Eu amo construir automação. Isso me faz sentir tudo quente por dentro. Tenho usado o TeamCity nas últimas semanas para configurar a automação de construções para muitos de nossos projetos atuais e está funcionando muito bem. O que é bom sobre o TeamCity Fácil de configurar com excelentes resultados? Fornece toneladas de informações e gráficos sobre suas compilações Altamente flexível Integração com rastreadores de bugs Plug-in para VS para commit pré-testado Notificador de bandeja do Windows Queríamos usar o psake como nosso Crie a ferramenta de script porque o XML é muito detalhado para essa tarefa e o PowerShell nos fornece o máximo de poder de script que podemos precisar. Configurar o psake para construir nossas soluções é relativamente trivial: O resultado da chamada invoke-psake build. ps1 Build: Ok, então podemos construir e testar nosso aplicativo usando o psake e obter feedback visual. Ótimo. Agora queremos executar essa construção no TeamCity. Conseguir Executar em TeamCity Isso não é um pedaço de bolo. Imediatamente, há um problema documentado com o PowerShell que impede que ele seja executado simplesmente colocando o PowerShell no campo executável Command: Isso faz com que o TeamCity seja interrompido indefinidamente, já que o PowerShell parece aguardar pela entrada. Ele nem parece acionar a detecção de builds enforcados. A solução é usar um arquivo em lotes (nomeio Build. bat) para invocar o PowerShell e passar algo sem sentido para o PowerShell ao invocá-lo: run-psake. ps1 é um script do PowerShell que garante que o ambiente seja configurado, ou seja, garante o módulo psake é carregado e, em seguida, executa invoke-psake: Agora, podemos definir o executável Command simplesmente para Build. bat: Agora o TeamCity executará a compilação, mas não relatará falhas de compilação, falhas de teste ou métricas de compilação. Você pode obter alguns elogios de seu chefe quando cada construção é reportada como Sucesso, independentemente de ser compilada ou passar nos testes, mas não irá ajudá-lo a entregar seu projeto. Provavelmente, existem várias maneiras de resolver isso e vou detalhar o método que encontrei no meu próximo post. Eu entendo que todo mundo que lê isso acha que o código de controle da fonte é essencial. Nem todo mundo sente o mesmo sobre o controle de origem do banco de dados, ou talvez eles o façam, mas eles não sabem como fazê-lo. Qual é o problema? Mesmo na minha curta carreira, tive mais do que suficiente exposição ao banco de dados compartilhado. Com mais de um desenvolvedor em um projeto, o gerenciamento de alterações no banco de dados é incrivelmente demorado e propenso a erros se feito manualmente, mesmo com um responsável dedicado pelo esquema. Com um único desenvolvedor em um projeto, não ter uma maneira simples de gerenciar e controlar as alterações ainda é complicado. O problema vem do fato de que, à medida que um sistema evolui, o banco de dados é alterado. É importante que essas alterações sejam comunicadas entre os membros da equipe para que, quando executarem a compilação local, ou menos prováveis, os testes de integração, que o aplicativo não seja interrompido devido a uma coluna ou tabela ausente. Algumas pessoas inteligentes podem ter a ideia de ter um único banco de dados no qual todos trabalham, de modo que haja apenas uma versão do banco de dados. Ótimo, problema resolvido. Isso é até que alguém queira fazer uma mudança. Não tendo muita alternativa, eles editam o banco de dados compartilhado e, de repente, todos quebram as construções locais. Ou várias pessoas depuram ao mesmo tempo usando o banco de dados compartilhado. Ao fazer isso, você pode garantir comportamentos estranhos ou deadlocks. Pior ainda, se você tiver um guardião, pode esperar até a próxima terça-feira para aplicar sua mudança urgente, prejudicando sua produtividade. Os proponentes compartilhados do banco de dados farão com que você acredite que há dados no banco de dados necessários para o aplicativo ser executado. Essas pessoas são tolas e precisam abrir os olhos para as maravilhas dos testes de unidade e testes de integração. É a lógica da aplicação que estava desenvolvendo, não os dados. Provavelmente, alguns dados são necessários para que um aplicativo seja executado (dados estáticos do AKA). Isso pode ser tratado de outras maneiras. Se você optar pela abordagem do banco de dados compartilhado, como você sabe em qual versão do esquema você está? Quão confiante é que Johnny não mudou o tipo de dados nessa coluna ou excluiu alguns dados críticos de pesquisa? Há poucas garantias de trabalhar em dessa maneira. Finalmente, como você implanta sem esforço o banco de dados em vários ambientes diferentes A primeira vez é fácil, basta fazer um backup e restaurar (barf, não tome isso como um conselho). Mas o que então Os diferentes ambientes terão dados neles para que você não possa mais fazer backup / restaurar. Então você está com um script de mudança, escrito manualmente ou gerado por uma ferramenta. O último é provavelmente ok para algumas pessoas e pode funcionar para você, mas ainda é um processo bastante manual. Ainda não resolve os problemas anteriores no entanto. Em resumo, é criminoso limítrofe usar um banco de dados compartilhado para desenvolvimento. Por banco de dados compartilhado, quero dizer qualquer coisa que não seja um banco de dados local dedicado para mim. É igualmente criminoso não controlar o banco de dados. Qual é a solução Existem alguns requisitos-chave que eu acho que precisam ser resolvidos para resolver esses problemas. A solução precisa ser simples Implementável em vários ambientes Capaz de recriar ou atualizar o banco de dados Executável em linha de comando (para compilações, scripts e testes de integração, etc.) Eu dei ao VSTS Database Edition uma boa solução e embora seja uma solução decente Em geral, eu realmente não gosto do mecanismo de implantação. É difícil implantar o banco de dados fora do IDE, e é por isso que o restante deste post não é sobre isso. Minha solução segue a orientação de K. Scott Allens sobre bancos de dados de versão. É uma implementação personalizada que empresta muitas ideias do projeto Tarantino. A configuração necessária para o implementador do Tarantino é menos que elegante e parece ter uma dependência do Nant e do Redgate SQL Compare, nenhum dos quais usamos internamente. Como funciona Cada conjunto de alterações no nosso esquema de banco de dados é roteirizado em um arquivo separado. Se um desenvolvedor quiser adicionar duas tabelas e excluir uma coluna, ele poderá criar um script SQL desses comandos. O script deve existir em uma pasta específica e seguir a convenção de nomenclatura XXXSomeDescription. sql, em que XXX é um número incrementado manualmente. Esse script é registrado no controle de origem da mesma maneira que qualquer outro arquivo. Procedimentos armazenados, visualizações e acionadores são roteirizados separadamente para um diretório diferente. Os dados estáticos são roteirizados como instruções simples de inserção / atualização condicional em um terceiro diretório. A ferramenta em si é um executável de linha de comando que possui dois modos de operação redefinidos e atualizados. Redefinir descarta o banco de dados completamente e o recria a partir dos scripts de mudança. Ele também adiciona uma tabela de log ao banco de dados para rastrear qual é a versão atual. A atualização examina essa tabela de log e executa apenas os scripts de alteração que não foram executados. Todos os scripts são executados transacionalmente, portanto, se algum falhar, eles serão revertidos e a execução posterior será interrompida. Uma regra deste sistema é que os desenvolvedores nunca editam um script depois de fazer o check-in. Então, como essa solução suporta várias configurações de ambiente? Bem, cada ambiente é configurado em um arquivo de configuração chamado MyConfiguration. deploy. Esses arquivos são parecidos com isto: Executando a Ferramenta Ao executar a ferramenta, você especifica uma configuração para implantar e procura no arquivo. deploy apropriado para as configurações. A configuração padrão é especificada no deployer. exe. config para a ferramenta, o que significa que a implementação mais comum (presumivelmente a local) pode ser executada apenas executando o exe. As opções da linha de comando estão abaixo Isso pode ser facilmente executado em qualquer lugar. O processo para alterar o banco de dados é adicionar um novo script de mudança e executar o executável. Simples Esta é uma sessão típica para a ferramenta. Não é particularmente chique, mas faz o trabalho. O primeiro comando eliminará e recriará o banco de dados Development até a versão 3. O segundo comando atualiza o banco de dados a partir dele. Observe como as visualizações e os procedimentos armazenados são recriados nas duas vezes. Essa é a tabela de migração no banco de dados, fornecendo todas as informações necessárias para o controle de versão. Testes de Integração e Construções de CI Para o teste de integração, apenas executamos algo semelhante ao abaixo no método SetUp de montagem. Portanto, toda vez que executamos nossos testes de integração, obtemos um novo banco de dados para testar. Isso também pode ser usado para implantações automatizadas do servidor de IC, mas eu prefiro executar manualmente as alterações do banco de dados em ambientes que não sejam de desenvolvimento, pois eles geralmente estão mais envolvidos. Esta é claramente uma área para melhoria. Escrever um mecanismo de implantação como esse é realmente simples. Se você tem um conhecimento decente do ADO. NET e segue a convenção sobre a configuração, não deve demorar mais do que um dia ou dois para ser escrito. Se você não tem uma solução para controle de fonte de banco de dados, considere as soluções existentes, como VSTS Database Edition, Tarantino ou Migrator. Net, para citar apenas algumas ou, se você gosta de esticar suas habilidades, jogue algo assim junto. Eu gostei do desafio. Pós-navegação
No comments:
Post a Comment