问:
Error while creating a Register Form using UserManager and SignInManager in an ASP.NET core application
I'm trying to create a register form using UserManager and SignInManager, however I am stuck with an error.

An unhandled exception occurred while processing the request.

InvalidOperationException: Unable to resolve service for type
  'Microsoft.AspNetCore.Identity.UserManager`1[Microsoft.AspNetCore.Identity.IdentityUser]'
  while attempting to activate
  'ProjectApplicationX00140684.Controllers.AccountController'.

Here is my AccountController:

namespace ProjectApplicationX00140684.Controllers
{
    public class AccountController : Controller
    {
        private readonly UserManager<IdentityUser> userManager;
        private readonly SignInManager<IdentityUser> signInManager;

        public AccountController(UserManager<IdentityUser> userManager,
            SignInManager<IdentityUser> signInManager)
        {
            this.userManager = userManager;
            this.signInManager = signInManager;
        }

        [HttpGet]
        public IActionResult Register()
        {
            return View();
        }

        [HttpPost]
        public async Task<IActionResult> Register(Register model)
        {
            if (ModelState.IsValid)
            {
                // Copy data from RegisterViewModel to IdentityUser
                var user = new IdentityUser
                {
                    UserName = model.Email,
                    Email = model.Email
                };

                // Store user data in AspNetUsers database table
                var result = await userManager.CreateAsync(user, model.Password);

                // If user is successfully created, sign-in the user using
                // SignInManager and redirect to index action of HomeController
                if (result.Succeeded)
                {
                    await signInManager.SignInAsync(user, isPersistent: false);
                    return RedirectToAction("index", "home");
                }

                // If there are any errors, add them to the ModelState object
                // which will be displayed by the validation summary tag helper
                foreach (var error in result.Errors)
                {
                    ModelState.AddModelError(string.Empty, error.Description);
                }
            }

            return View(model);
        }
    }
}
```

<p>Here is my Startup.cs</p>

<pre class="lang-cs prettyprint-override"><code>namespace ProjectApplicationX00140684
{
    public class Startup
    {
        public Startup(IConfiguration configuration)
        {
            Configuration = configuration;
        }

        public IConfiguration Configuration { get; }

        // This method gets called by the runtime. Use this method to add services to the container.
        public void ConfigureServices(IServiceCollection services)
        {

            services.Configure<CookiePolicyOptions>(options =>
            {
                // This lambda determines whether user consent for non-essential cookies is needed for a given request.
                options.CheckConsentNeeded = context => true;
                options.MinimumSameSitePolicy = SameSiteMode.None;
            });

            services.AddDbContext<VehicleContext>(options =>
        options.UseSqlServer(Configuration.GetConnectionString("DefaultConnection")));

            services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_2);
        }

        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
        public void Configure(IApplicationBuilder app, IHostingEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
            }
            else
            {
                app.UseExceptionHandler("/Home/Error");
                // The default HSTS value is 30 days. You may want to change this for production scenarios, see https://aka.ms/aspnetcore-hsts.
                app.UseHsts();
            }

            app.UseHttpsRedirection();
            app.UseStaticFiles();
            app.UseCookiePolicy();

            app.UseMvc(routes =>
            {
                routes.MapRoute(
                    name: "default",
                    template: "{controller=Home}/{action=Index}/{id?}");
            });
        }
    }
}
</code>```

答:
You should configure Identity services , services are added in ConfigureServices method :

```<code>services.AddDbContext<ApplicationDbContext>(options =>
    options.UseSqlServer(
        Configuration.GetConnectionString("DefaultConnection")));
services.AddDefaultIdentity<IdentityUser>()
    .AddDefaultUI(UIFramework.Bootstrap4)
    .AddEntityFrameworkStores<ApplicationDbContext>();
</code>```

ApplicationDbContext.cs:

```<code>public class ApplicationDbContext : IdentityDbContext
{
    public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options)
        : base(options)
    {
    }
}
</code>```

And add authentication middleware to the request pipeline:

```<code>app.UseAuthentication();
</code>```

After that you can apply migrations(Update-Database) to update database
Please refer to document for more details and code sample :

https://learn.microsoft.com/en-us/aspnet/core/security/authentication/identity?view=aspnetcore-2.2&tabs=visual-studio

Body:
I'm trying to create a register form using UserManager and SignInManager, however I am stuck with an error.

An unhandled exception occurred while processing the request.

InvalidOperationException: Unable to resolve service for type
  'Microsoft.AspNetCore.Identity.UserManager`1[Microsoft.AspNetCore.Identity.IdentityUser]'
  while attempting to activate
  'ProjectApplicationX00140684.Controllers.AccountController'.

Here is my AccountController:

namespace ProjectApplicationX00140684.Controllers
{
    public class AccountController : Controller
    {
        private readonly UserManager<IdentityUser> userManager;
        private readonly SignInManager<IdentityUser> signInManager;

        public AccountController(UserManager<IdentityUser> userManager,
            SignInManager<IdentityUser> signInManager)
        {
            this.userManager = userManager;
            this.signInManager = signInManager;
        }

        [HttpGet]
        public IActionResult Register()
        {
            return View();
        }

        [HttpPost]
        public async Task<IActionResult> Register(Register model)
        {
            if (ModelState.IsValid)
            {
                // Copy data from RegisterViewModel to IdentityUser
                var user = new IdentityUser
                {
                    UserName = model.Email,
                    Email = model.Email
                };

                // Store user data in AspNetUsers database table
                var result = await userManager.CreateAsync(user, model.Password);

                // If user is successfully created, sign-in the user using
                // SignInManager and redirect to index action of HomeController
                if (result.Succeeded)
                {
                    await signInManager.SignInAsync(user, isPersistent: false);
                    return RedirectToAction("index", "home");
                }

                // If there are any errors, add them to the ModelState object
                // which will be displayed by the validation summary tag helper
                foreach (var error in result.Errors)
                {
                    ModelState.AddModelError(string.Empty, error.Description);
                }
            }

            return View(model);
        }
    }
}

Here is my Startup.cs

namespace ProjectApplicationX00140684
{
    public class Startup
    {
        public Startup(IConfiguration configuration)
        {
            Configuration = configuration;
        }

        public IConfiguration Configuration { get; }

        // This method gets called by the runtime. Use this method to add services to the container.
        public void ConfigureServices(IServiceCollection services)
        {

            services.Configure<CookiePolicyOptions>(options =>
            {
                // This lambda determines whether user consent for non-essential cookies is needed for a given request.
                options.CheckConsentNeeded = context => true;
                options.MinimumSameSitePolicy = SameSiteMode.None;
            });

            services.AddDbContext<VehicleContext>(options =>
        options.UseSqlServer(Configuration.GetConnectionString("DefaultConnection")));

            services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_2);
        }

        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
        public void Configure(IApplicationBuilder app, IHostingEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
            }
            else
            {
                app.UseExceptionHandler("/Home/Error");
                // The default HSTS value is 30 days. You may want to change this for production scenarios, see https://aka.ms/aspnetcore-hsts.
                app.UseHsts();
            }

            app.UseHttpsRedirection();
            app.UseStaticFiles();
            app.UseCookiePolicy();

            app.UseMvc(routes =>
            {
                routes.MapRoute(
                    name: "default",
                    template: "{controller=Home}/{action=Index}/{id?}");
            });
        }
    }
}

Body:
You should configure Identity services , services are added in ConfigureServices method :

services.AddDbContext<ApplicationDbContext>(options =>
    options.UseSqlServer(
        Configuration.GetConnectionString("DefaultConnection")));
services.AddDefaultIdentity<IdentityUser>()
    .AddDefaultUI(UIFramework.Bootstrap4)
    .AddEntityFrameworkStores<ApplicationDbContext>();

ApplicationDbContext.cs:

public class ApplicationDbContext : IdentityDbContext
{
    public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options)
        : base(options)
    {
    }
}

And add authentication middleware to the request pipeline:

app.UseAuthentication();

After that you can apply migrations(Update-Database) to update database
Please refer to document for more details and code sample :

https://learn.microsoft.com/en-us/aspnet/core/security/authentication/identity?view=aspnetcore-2.2&tabs=visual-studio


来源: stackexchange

问:
Erro uploading Excel to Google Cloud Storage
I'm using the 'exceljs' lib. It's work great on my local node server. Now I'm trying to use Firebase Functions to upload the excel file to Google Cloud storage.

This is the entire code I'm using:

```<code>'use strict';
const functions = require('firebase-functions');
const admin = require('firebase-admin');
const ExcelJS = require('exceljs');

admin.initializeApp();

var workbook = new ExcelJS.Workbook();
var worksheet = workbook.addWorksheet('Relatório Consolidado');

function startExcel(){

  worksheet.columns = [
    { header: 'Empresa', key: 'empresa', width: 25 },
    { header: 'Data criação', key: 'data_criacao', width: 25 },
    { header: 'Responsável agendamento', key: 'agendador', width: 25 },
    { header: 'Colaborador', key: 'colaborador', width: 25 },
    { header: 'Endereço', key: 'endereco', width: 25 },
    { header: 'CPF', key: 'cpf', width: 25 },
    { header: 'CTPS', key: 'ctps', width: 25 },
    { header: 'Função', key: 'funcao', width: 25 },

    { header: 'Data agendado', key: 'nome_subtipo_produto', width: 25 },
    { header: 'Data atendimento médico', key: 'nome_subtipo_produto', width: 25 },
    { header: 'Data inicio atendimento', key: 'nome_subtipo_produto', width: 25 },
    { header: 'Data inicio exames', key: 'nome_subtipo_produto', width: 25 },
    { header: 'Tipo de exame', key: 'valor_produto', width: 25 },
    { header: 'Exames realizados', key: 'valor_produto', width: 25 },
    { header: 'Status atendimento', key: 'tipoPagamento', width: 25 },
    { header: 'Status exames', key: 'centroCustoStr', width: 25 }
  ];
}

function salvaExcel(){

  return new Promise(function(resolve, reject){

      let filename = `/tmp/Relatorio.xlsx`
      let bucketName = 'gs://xxx.appspot.com/Relatorios'
      const bucket = admin.storage().bucket(bucketName);

      workbook.xlsx.writeFile(filename)
      .then(() => {

      console.log('Excel criado com sucesso! Enviando upload do arquivo: ' + filename)

        const metadata = {
          contentType: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
        };

        bucket.upload(filename, metadata)

        .then(() => {
          const theFile = bucket.file(filename);
          theFile.getSignedURL(signedUrlOptions)

          .then((signedUrl) => {
            resolve(signedUrl)
          });

        })
        .catch((error) => {
          reject('Erro ao realizar upload: ' + error)
        })
      })

      .catch((error) => {
        reject('Erro ao realizar upload: ' + error)
      })

  })
}

startExcel()

/**********************************
 * Relatórios
 ********************************/

function relatorios(change, context){

  return new Promise((resolve, reject) => {

    const snapshot = change.after
    const data = snapshot.val()

    verificaRelatorioAgendamentos(change)

    .then(() => {
      resolve()

    })

    .catch((error => {
      reject(error)

    }))

  })
}

function verificaRelatorioAgendamentos(change, context){

  return new Promise((resolve, reject) => {

    const snapshot = change.after
    const data = snapshot.val()
    const dataInicial = data.dataInicial
    const year = moment(dataInicial).format('YYYY')
    const month = moment(dataInicial).format('MM')
    const state = 'DF'
    let path = "/agendamentos/" + state + "/" +  year + "/" + month

    const relatorios = admin.database().ref(path).once('value');

    return Promise.all([relatorios])

      .then(results => {

        let valores = results[0]
        criaRelatorioAgendamentos(valores)

        .then(() => {
          resolve()

        })

        .catch((error => {
          reject(error)

        }))

    })

  })

}

function criaRelatorioAgendamentos(results){

  return new Promise((resolve, reject) => {

    let promises = []

    results.forEach(element => {

      let promise = new Promise(function(resolveExcel){

        let data = element.val()

        worksheet.addRow({
          id: 1,
          empresa: data.agendador.company,
          data_criacao: data.dataCriacao,
          agendador: data.agendador.nome,
          colaborador: data.colaborador.nome,
          cpf: data.colaborador.cpf,
          ctps: data.colaborador.ctps,
          funcao: data.colaborador.funcao,
          data_agendado: data.data,
          data_atendimento_medico: data.dataAtendimento,
          data_inicio_atendimento: data.dataInicio,
          data_inicio_exames: data.dataInicioExames,
          tipo_exame: data.tipoExame,
          exames: data.exames[0].nome,
          status_atendimento: data.status,
          status_exames: data.statusExames

        })

        resolveExcel()

      })

      promises.push(promise)

    })

    Promise.all(promises)

      .then(() => {
        salvaExcel()

        .then((url) => {

          console.log('Salvar URL' + url)

          resolve(url)

        })

        .catch((error => {
          reject(error)

        }))

    })

  })

}

exports.relatorios = functions.database.ref('/relatorios/{state}/{year}/{month}/{relatoriosId}')
    .onWrite((change, context) => {
      return relatorios(change, context)
});
</code>```

On Functions console, the log show me that the excel file was created successfully. But when uploading, a very strange error pops:

What I'm doing wrong? I apreciate any help.

Thanks!

答:
The error message you are getting comes from trying to get the signed URL of a non-existant file.

When you call bucket.upload(filename, metadata), you are uploading the file /tmp/Relatorio.xlsx, which creates a file in your bucket called Relatorio.xlsx. On the next line you call bucket.file(filename); which incorrectly associates itself with /tmp/Relatorio.xlsx instead of Relatorio.xlsx.

To fix this, you should use the File object that is resolved from bucket.upload() instead of creating it yourself:

```<code>bucket.upload(filename, metadata)
    .then((file) => file.getSignedURL())
    .then((url) => {
        console.log('Salvar URL' + url)
    })
</code>```

Other notes and fixes

Your code also contains a lot of unnecessary new Promise((resolve, reject) => { ... }) calls. This is called the Promise constructor anti-pattern and most of them can be removed by properly chaining the Promises. This blog post is a good crash course on Promises and how to use them properly.

Regarding your function's source code, as the index.js file for functions will contain multiple function definitions, you should not define variables at the top of your index.js file unless they are shared by all of your functions and they are stateless in case a function is called multiple times. This is particularly important when dealing with I/O or memory-intensive resources such as files.

With your current code, if the relatorios function was called twice in a short period, the saved file would contain both the old data from the first call and the new data from the current call leading to both an invalid file and a potential memory leak.

Removing the excessive promise calls and making it so that your exceljs code can be rerun without corrupting any data results in the following index.js file:

```<code>'use strict';
const functions = require('firebase-functions');
const admin = require('firebase-admin');
// 'exceljs' is required on-demand in MyExcelSheetHelper

admin.initializeApp();

/* HELPER CLASS */

/**
 * A helper class used to create reuseable functions that won't
 * conflict with each other
 */
class MyExcelSheetHelper {

  constructor() {
    const ExcelJS = require('exceljs');

    this.workbook = new ExcelJS.Workbook();
    this.worksheet = this.workbook.addWorksheet('Relatório Consolidado');

    this.worksheet.columns = [
      { header: 'Empresa', key: 'empresa', width: 25 },
      { header: 'Data criação', key: 'data_criacao', width: 25 },
      { header: 'Responsável agendamento', key: 'agendador', width: 25 },
      { header: 'Colaborador', key: 'colaborador', width: 25 },
      { header: 'Endereço', key: 'endereco', width: 25 },
      { header: 'CPF', key: 'cpf', width: 25 },
      { header: 'CTPS', key: 'ctps', width: 25 },
      { header: 'Função', key: 'funcao', width: 25 },

      { header: 'Data agendado', key: 'nome_subtipo_produto', width: 25 },
      { header: 'Data atendimento médico', key: 'nome_subtipo_produto', width: 25 },
      { header: 'Data inicio atendimento', key: 'nome_subtipo_produto', width: 25 },
      { header: 'Data inicio exames', key: 'nome_subtipo_produto', width: 25 },
      { header: 'Tipo de exame', key: 'valor_produto', width: 25 },
      { header: 'Exames realizados', key: 'valor_produto', width: 25 },
      { header: 'Status atendimento', key: 'tipoPagamento', width: 25 },
      { header: 'Status exames', key: 'centroCustoStr', width: 25 }
    ];
  }

  /**
   * Streams this workbook to Cloud Storage
   * @param storageFilepath - the relative path where the file is uploaded to Cloud Storage
   * @returns the signed URL for the file
   */
  salva(storageFilepath) {
    if (!storageFilepath) {
      return Promise.reject(new Error('storageFilepath is required'));
    }

    const bucket = admin.storage().bucket();

    const storageFile = bucket.file(storageFilepath);

    const uploadFilePromise = new Promise((resolve, reject) => {
      try {
        const stream = storageFile.createWriteStream({
          contentType: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
        });

        stream.on('finish', () => {
          resolve();
        });

        stream.on('error', error => {
          reject(error);
        });

        this.workbook.xlsx.write(stream)
          .then(() => {
            stream.end();
          });

      } catch (e) { // catches errors from createWriteStream
        reject(e);
      }
    })

    return uploadFilePromise
      .then(() => {
        var CONFIG = {
          action: 'read',
          expires: '03-01-2500',
        };

        bucket.file(storageFilepath).getSignedUrl(CONFIG)
        .then((signedUrl) => {

          return signedUrl
        })
      })

  }
}

/* FUNCTIONS CODE */

function criaRelatorioAgendamentos(path, querySnapshot) {
  const excelFileHelper = new MyExcelSheetHelper();
  const worksheet = excelFile.worksheet;

  // this forEach loop is synchronous, so no Promises are needed here
  querySnapshot.forEach(entrySnapshot => {
    const data = entrySnapshot.val();

    worksheet.addRow({
      id: 1,
      empresa: data.agendador.company,
      data_criacao: data.dataCriacao,
      agendador: data.agendador.nome,
      colaborador: data.colaborador.nome,
      cpf: data.colaborador.cpf,
      ctps: data.colaborador.ctps,
      funcao: data.colaborador.funcao,
      data_agendado: data.data,
      data_atendimento_medico: data.dataAtendimento,
      data_inicio_atendimento: data.dataInicio,
      data_inicio_exames: data.dataInicioExames,
      tipo_exame: data.tipoExame,
      exames: data.exames[0].nome,
      status_atendimento: data.status,
      status_exames: data.statusExames
    });
  });

  return excelFileHelper.salva(path + '/Relatorio.xlsx');
}

exports.relatorios = functions.database.ref('/relatorios/{state}/{year}/{month}/{relatoriosId}')
    .onWrite((change, context) => {

    // Verificar relatorio agendamentos

    const snapshot = change.after;
    const data = snapshot.val();
    const dataInicial = data.dataInicial;
    const year = moment(dataInicial).format('YYYY');
    const month = moment(dataInicial).format('MM');
    const state = 'DF';
    const path = "/agendamentos/" + state + "/" +  year + "/" + month;

    return admin.database().ref(path).once('value')
      .then(valores => {
        return criaRelatorioAgendamentos(path, valores);
      });
});
</code>```

ContentLicense: CC BY-SA 4.0

Body:
I'm using the 'exceljs' lib. It's work great on my local node server. Now I'm trying to use Firebase Functions to upload the excel file to Google Cloud storage.

This is the entire code I'm using:

'use strict';
const functions = require('firebase-functions');
const admin = require('firebase-admin');
const ExcelJS = require('exceljs');

admin.initializeApp();

var workbook = new ExcelJS.Workbook();
var worksheet = workbook.addWorksheet('Relatório Consolidado');

function startExcel(){

  worksheet.columns = [
    { header: 'Empresa', key: 'empresa', width: 25 },
    { header: 'Data criação', key: 'data_criacao', width: 25 },
    { header: 'Responsável agendamento', key: 'agendador', width: 25 },
    { header: 'Colaborador', key: 'colaborador', width: 25 },
    { header: 'Endereço', key: 'endereco', width: 25 },
    { header: 'CPF', key: 'cpf', width: 25 },
    { header: 'CTPS', key: 'ctps', width: 25 },
    { header: 'Função', key: 'funcao', width: 25 },

    { header: 'Data agendado', key: 'nome_subtipo_produto', width: 25 },
    { header: 'Data atendimento médico', key: 'nome_subtipo_produto', width: 25 },
    { header: 'Data inicio atendimento', key: 'nome_subtipo_produto', width: 25 },
    { header: 'Data inicio exames', key: 'nome_subtipo_produto', width: 25 },
    { header: 'Tipo de exame', key: 'valor_produto', width: 25 },
    { header: 'Exames realizados', key: 'valor_produto', width: 25 },
    { header: 'Status atendimento', key: 'tipoPagamento', width: 25 },
    { header: 'Status exames', key: 'centroCustoStr', width: 25 }
  ];
}

function salvaExcel(){

  return new Promise(function(resolve, reject){

      let filename = `/tmp/Relatorio.xlsx`
      let bucketName = 'gs://xxx.appspot.com/Relatorios'
      const bucket = admin.storage().bucket(bucketName);

      workbook.xlsx.writeFile(filename)
      .then(() => {

      console.log('Excel criado com sucesso! Enviando upload do arquivo: ' + filename)

        const metadata = {
          contentType: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
        };

        bucket.upload(filename, metadata)

        .then(() => {
          const theFile = bucket.file(filename);
          theFile.getSignedURL(signedUrlOptions)

          .then((signedUrl) => {
            resolve(signedUrl)
          });

        })
        .catch((error) => {
          reject('Erro ao realizar upload: ' + error)
        })
      })

      .catch((error) => {
        reject('Erro ao realizar upload: ' + error)
      })

  })
}

startExcel()

/**********************************
 * Relatórios
 ********************************/

function relatorios(change, context){

  return new Promise((resolve, reject) => {

    const snapshot = change.after
    const data = snapshot.val()

    verificaRelatorioAgendamentos(change)

    .then(() => {
      resolve()

    })

    .catch((error => {
      reject(error)

    }))

  })
}

function verificaRelatorioAgendamentos(change, context){

  return new Promise((resolve, reject) => {

    const snapshot = change.after
    const data = snapshot.val()
    const dataInicial = data.dataInicial
    const year = moment(dataInicial).format('YYYY')
    const month = moment(dataInicial).format('MM')
    const state = 'DF'
    let path = "/agendamentos/" + state + "/" +  year + "/" + month

    const relatorios = admin.database().ref(path).once('value');

    return Promise.all([relatorios])

      .then(results => {

        let valores = results[0]
        criaRelatorioAgendamentos(valores)

        .then(() => {
          resolve()

        })

        .catch((error => {
          reject(error)

        }))

    })

  })

}

function criaRelatorioAgendamentos(results){

  return new Promise((resolve, reject) => {

    let promises = []

    results.forEach(element => {

      let promise = new Promise(function(resolveExcel){

        let data = element.val()

        worksheet.addRow({
          id: 1,
          empresa: data.agendador.company,
          data_criacao: data.dataCriacao,
          agendador: data.agendador.nome,
          colaborador: data.colaborador.nome,
          cpf: data.colaborador.cpf,
          ctps: data.colaborador.ctps,
          funcao: data.colaborador.funcao,
          data_agendado: data.data,
          data_atendimento_medico: data.dataAtendimento,
          data_inicio_atendimento: data.dataInicio,
          data_inicio_exames: data.dataInicioExames,
          tipo_exame: data.tipoExame,
          exames: data.exames[0].nome,
          status_atendimento: data.status,
          status_exames: data.statusExames

        })

        resolveExcel()

      })

      promises.push(promise)

    })

    Promise.all(promises)

      .then(() => {
        salvaExcel()

        .then((url) => {

          console.log('Salvar URL' + url)

          resolve(url)

        })

        .catch((error => {
          reject(error)

        }))

    })

  })

}

exports.relatorios = functions.database.ref('/relatorios/{state}/{year}/{month}/{relatoriosId}')
    .onWrite((change, context) => {
      return relatorios(change, context)
});

On Functions console, the log show me that the excel file was created successfully. But when uploading, a very strange error pops:

What I'm doing wrong? I apreciate any help.

Thanks!

Body:
The error message you are getting comes from trying to get the signed URL of a non-existant file.

When you call bucket.upload(filename, metadata), you are uploading the file /tmp/Relatorio.xlsx, which creates a file in your bucket called Relatorio.xlsx. On the next line you call bucket.file(filename); which incorrectly associates itself with /tmp/Relatorio.xlsx instead of Relatorio.xlsx.

To fix this, you should use the File object that is resolved from bucket.upload() instead of creating it yourself:

bucket.upload(filename, metadata)
    .then((file) => file.getSignedURL())
    .then((url) => {
        console.log('Salvar URL' + url)
    })

Other notes and fixes

Your code also contains a lot of unnecessary new Promise((resolve, reject) => { ... }) calls. This is called the Promise constructor anti-pattern and most of them can be removed by properly chaining the Promises. This blog post is a good crash course on Promises and how to use them properly.

Regarding your function's source code, as the index.js file for functions will contain multiple function definitions, you should not define variables at the top of your index.js file unless they are shared by all of your functions and they are stateless in case a function is called multiple times. This is particularly important when dealing with I/O or memory-intensive resources such as files.

With your current code, if the relatorios function was called twice in a short period, the saved file would contain both the old data from the first call and the new data from the current call leading to both an invalid file and a potential memory leak.

Removing the excessive promise calls and making it so that your exceljs code can be rerun without corrupting any data results in the following index.js file:

'use strict';
const functions = require('firebase-functions');
const admin = require('firebase-admin');
// 'exceljs' is required on-demand in MyExcelSheetHelper

admin.initializeApp();

/* HELPER CLASS */

/**
 * A helper class used to create reuseable functions that won't
 * conflict with each other
 */
class MyExcelSheetHelper {

  constructor() {
    const ExcelJS = require('exceljs');

    this.workbook = new ExcelJS.Workbook();
    this.worksheet = this.workbook.addWorksheet('Relatório Consolidado');

    this.worksheet.columns = [
      { header: 'Empresa', key: 'empresa', width: 25 },
      { header: 'Data criação', key: 'data_criacao', width: 25 },
      { header: 'Responsável agendamento', key: 'agendador', width: 25 },
      { header: 'Colaborador', key: 'colaborador', width: 25 },
      { header: 'Endereço', key: 'endereco', width: 25 },
      { header: 'CPF', key: 'cpf', width: 25 },
      { header: 'CTPS', key: 'ctps', width: 25 },
      { header: 'Função', key: 'funcao', width: 25 },

      { header: 'Data agendado', key: 'nome_subtipo_produto', width: 25 },
      { header: 'Data atendimento médico', key: 'nome_subtipo_produto', width: 25 },
      { header: 'Data inicio atendimento', key: 'nome_subtipo_produto', width: 25 },
      { header: 'Data inicio exames', key: 'nome_subtipo_produto', width: 25 },
      { header: 'Tipo de exame', key: 'valor_produto', width: 25 },
      { header: 'Exames realizados', key: 'valor_produto', width: 25 },
      { header: 'Status atendimento', key: 'tipoPagamento', width: 25 },
      { header: 'Status exames', key: 'centroCustoStr', width: 25 }
    ];
  }

  /**
   * Streams this workbook to Cloud Storage
   * @param storageFilepath - the relative path where the file is uploaded to Cloud Storage
   * @returns the signed URL for the file
   */
  salva(storageFilepath) {
    if (!storageFilepath) {
      return Promise.reject(new Error('storageFilepath is required'));
    }

    const bucket = admin.storage().bucket();

    const storageFile = bucket.file(storageFilepath);

    const uploadFilePromise = new Promise((resolve, reject) => {
      try {
        const stream = storageFile.createWriteStream({
          contentType: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
        });

        stream.on('finish', () => {
          resolve();
        });

        stream.on('error', error => {
          reject(error);
        });

        this.workbook.xlsx.write(stream)
          .then(() => {
            stream.end();
          });

      } catch (e) { // catches errors from createWriteStream
        reject(e);
      }
    })

    return uploadFilePromise
      .then(() => {
        var CONFIG = {
          action: 'read',
          expires: '03-01-2500',
        };

        bucket.file(storageFilepath).getSignedUrl(CONFIG)
        .then((signedUrl) => {

          return signedUrl
        })
      })

  }
}

/* FUNCTIONS CODE */

function criaRelatorioAgendamentos(path, querySnapshot) {
  const excelFileHelper = new MyExcelSheetHelper();
  const worksheet = excelFile.worksheet;

  // this forEach loop is synchronous, so no Promises are needed here
  querySnapshot.forEach(entrySnapshot => {
    const data = entrySnapshot.val();

    worksheet.addRow({
      id: 1,
      empresa: data.agendador.company,
      data_criacao: data.dataCriacao,
      agendador: data.agendador.nome,
      colaborador: data.colaborador.nome,
      cpf: data.colaborador.cpf,
      ctps: data.colaborador.ctps,
      funcao: data.colaborador.funcao,
      data_agendado: data.data,
      data_atendimento_medico: data.dataAtendimento,
      data_inicio_atendimento: data.dataInicio,
      data_inicio_exames: data.dataInicioExames,
      tipo_exame: data.tipoExame,
      exames: data.exames[0].nome,
      status_atendimento: data.status,
      status_exames: data.statusExames
    });
  });

  return excelFileHelper.salva(path + '/Relatorio.xlsx');
}

exports.relatorios = functions.database.ref('/relatorios/{state}/{year}/{month}/{relatoriosId}')
    .onWrite((change, context) => {

    // Verificar relatorio agendamentos

    const snapshot = change.after;
    const data = snapshot.val();
    const dataInicial = data.dataInicial;
    const year = moment(dataInicial).format('YYYY');
    const month = moment(dataInicial).format('MM');
    const state = 'DF';
    const path = "/agendamentos/" + state + "/" +  year + "/" + month;

    return admin.database().ref(path).once('value')
      .then(valores => {
        return criaRelatorioAgendamentos(path, valores);
      });
});


问:
Django redundancy and replication over two VPS accounts
I'm slowly getting into the position where one of my Django sites needs some robustness behind it. I'd currently running on a single VPS on a SQLite database with memcached.. It's about as un-scaled as things can get.

If I bought another VPS account, what would I want to do?

Move to MySQL/PostgreSQL with replication? What's easiest? Does replication protect me from one server exploding? Are there concurrency downsides?

How do I load-balance between the two servers?

I'd put memcached on the new server too. If I put both IPs into the configuration, would that keep a copy of data on both servers? (I'm thinking of what happens to session data - currently stored in memcached)

I'm currently using Cherokee as the httpd - I'm sure this has its own set of issues. If you've any tips, let me know.

Am I going at this the wrong way? Is there an easier way to have faster, more robust django sites?

答:
Watching the Django Deployment Workshop by Jacob Kaplan-Moss should give you a good overview.

MySQL supports Master-Slave and Master-Master setups I don't use PostgreSQL.

You can use nginx as your loadbalancer, HAProxy is an option, too (SO use it).

Memcached distributes the objects over the servers, If one crashes the data is lost.

I don't know Cherokee, but nginx is great.

ContentLicense: CC BY-SA 2.5

ContentLicense: CC BY-SA 3.0


问:
Removing spacing between Xamarin.Forms Grid Cells
I am struggling with removing spacing between grid cells. I have tried using ColumnSpacing="0" and RowSpacing = "0",however it does not make grid spaceless.

```<code><?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
                     xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
                     x:Class="XamarinPradmenys.CalculatorPage">
    <AbsoluteLayout>
        <StackLayout AbsoluteLayout.LayoutBounds="0,0,1,0.25" AbsoluteLayout.LayoutFlags="All" >
            <Label x:Name="live" FontSize="20"/>
            <Label x:Name="rez" FontSize="15"/>
        </StackLayout>

        <Grid RowSpacing="0" ColumnSpacing="0"  AbsoluteLayout.LayoutBounds="0,1,1,0.75" AbsoluteLayout.LayoutFlags="All">
            <Grid.RowDefinitions>
                <RowDefinition Height="Auto"/>
                <RowDefinition Height="*"/>
                <RowDefinition Height="*"/>
                <RowDefinition Height="*"/>
                <RowDefinition Height="*"/>
                <RowDefinition Height="*"/>
            </Grid.RowDefinitions>
            <Grid.ColumnDefinitions>
                <ColumnDefinition Width="Auto"/>
                <ColumnDefinition Width="*"/>
                <ColumnDefinition Width="*"/>
                <ColumnDefinition Width="*"/>
            </Grid.ColumnDefinitions>

            <Button Grid.Column="0" Grid.Row="0" Text="mc" />
            <Button Grid.Column="1" Grid.Row="0" Text="m+"/>
            <Button Grid.Column="2" Grid.Row="0" Text="m-"/>
            <Button Grid.Column="3" Grid.Row="0" Text="mr"/>
            <Button Grid.Column="0" Grid.Row="1" Text="C"/>
            <Button Grid.Column="1" Grid.Row="1" Text="/"/>
            <Button Grid.Column="2" Grid.Row="1" Text="X"/>
            <Button Grid.Column="3" Grid.Row="1" Text="Del"/>
            <Button Grid.Column="0" Grid.Row="2" Text="7"/>
            <Button Grid.Column="1" Grid.Row="2" Text="8"/>
            <Button Grid.Column="2" Grid.Row="2" Text="9"/>
            <Button Grid.Column="3" Grid.Row="2" Text="-"/>
            <Button Grid.Column="0" Grid.Row="3" Text="4"/>
            <Button Grid.Column="1" Grid.Row="3" Text="5"/>
            <Button Grid.Column="2" Grid.Row="3" Text="6"/>
            <Button Grid.Column="3" Grid.Row="3" Text="+"/>
            <Button Grid.Column="0" Grid.Row="4" Text="1"/>
            <Button Grid.Column="1" Grid.Row="4" Text="2"/>
            <Button Grid.Column="2" Grid.Row="4" Text="3"/>
            <Button Grid.Column="3" Grid.Row="4" Grid.RowSpan="2" Text="="/>
            <Button Grid.Column="0" Grid.Row="5" Text="%" />
            <Button Grid.Column="1" Grid.Row="5" Text="0"/>
            <Button Grid.Column="2" Grid.Row="5" Text=","/>
        </Grid>

    </AbsoluteLayout>
</ContentPage>
</code>```

That I get is:

As you can see there are spaces between every row and column. Do you have any suggestions?

Do you have anything what could help me?

答:
You could do this via custom renderer.

MyButton.cs

```<code> public class MyButton : Button
{
}
</code>```

MyButtonRenderer.cs

```<code> [assembly: ExportRenderer(typeof(MyButton), typeof(MyButtonRenderer))]
 namespace XamarinDemo.Droid
 {
   public class MyButtonRenderer : Xamarin.Forms.Platform.Android.AppCompat.ButtonRenderer
   {

    public MyButtonRenderer(Context context) : base(context)
    {

    }

    protected override void OnElementChanged(ElementChangedEventArgs<Xamarin.Forms.Button> e)
    {
        base.OnElementChanged(e);
        if (Control != null)
        {
            Control.Background = null;
            Control.SetBackgroundColor(Android.Graphics.Color.Gray);
        }
    }

    protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
    {
        base.OnElementPropertyChanged(sender, e);
        if (e.PropertyName == "BackgroundColor")
        {
            Control.SetBackgroundColor(Android.Graphics.Color.Gray);
        }
    }
  }
}
</code>```

Xaml

```<code> <AbsoluteLayout>
    <StackLayout AbsoluteLayout.LayoutBounds="0,0,1,0.25" AbsoluteLayout.LayoutFlags="All">
        <Label x:Name="live" FontSize="20" />
        <Label x:Name="rez" FontSize="15" />
    </StackLayout>

    <Grid
        AbsoluteLayout.LayoutBounds="0,1,1,0.75"
        AbsoluteLayout.LayoutFlags="All"
        ColumnSpacing="0"
        RowSpacing="0">
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto" />
            <RowDefinition Height="*" />
            <RowDefinition Height="*" />
            <RowDefinition Height="*" />
            <RowDefinition Height="*" />
            <RowDefinition Height="*" />
        </Grid.RowDefinitions>
        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="Auto" />
            <ColumnDefinition Width="*" />
            <ColumnDefinition Width="*" />
            <ColumnDefinition Width="*" />
        </Grid.ColumnDefinitions>

        <local:MyButton
            Grid.Row="0"
            Grid.Column="0"
            Text="mc" />
        <local:MyButton
            Grid.Row="0"
            Grid.Column="1"
            Text="m+" />
        <local:MyButton
            Grid.Row="0"
            Grid.Column="2"
            Text="m-" />
        <local:MyButton
            Grid.Row="0"
            Grid.Column="3"
            Text="mr" />
        <local:MyButton
            Grid.Row="1"
            Grid.Column="0"
            Text="C" />
        <local:MyButton
            Grid.Row="1"
            Grid.Column="1"
            Text="/" />
        <local:MyButton
            Grid.Row="1"
            Grid.Column="2"
            Text="X" />
        <local:MyButton
            Grid.Row="1"
            Grid.Column="3"
            Text="Del" />
        <local:MyButton
            Grid.Row="2"
            Grid.Column="0"
            Text="7" />
        <local:MyButton
            Grid.Row="2"
            Grid.Column="1"
            Text="8" />
        <local:MyButton
            Grid.Row="2"
            Grid.Column="2"
            Text="9" />
        <local:MyButton
            Grid.Row="2"
            Grid.Column="3"
            Text="-" />
        <local:MyButton
            Grid.Row="3"
            Grid.Column="0"
            Text="4" />
        <local:MyButton
            Grid.Row="3"
            Grid.Column="1"
            Text="5" />
        <local:MyButton
            Grid.Row="3"
            Grid.Column="2"
            Text="6" />
        <local:MyButton
            Grid.Row="3"
            Grid.Column="3"
            Text="+" />
        <local:MyButton
            Grid.Row="4"
            Grid.Column="0"
            Text="1" />
        <local:MyButton
            Grid.Row="4"
            Grid.Column="1"
            Text="2" />
        <local:MyButton
            Grid.Row="4"
            Grid.Column="2"
            Text="3" />
        <local:MyButton
            Grid.Row="4"
            Grid.RowSpan="2"
            Grid.Column="3"
            Text="=" />
        <local:MyButton
            Grid.Row="5"
            Grid.Column="0"
            Text="%" />
        <local:MyButton
            Grid.Row="5"
            Grid.Column="1"
            Text="0" />
        <local:MyButton
            Grid.Row="5"
            Grid.Column="2"
            Text="," />
    </Grid>

</AbsoluteLayout>
</code>```

Body:
I am struggling with removing spacing between grid cells. I have tried using ColumnSpacing="0" and RowSpacing = "0",however it does not make grid spaceless.

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
                     xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
                     x:Class="XamarinPradmenys.CalculatorPage">
    <AbsoluteLayout>
        <StackLayout AbsoluteLayout.LayoutBounds="0,0,1,0.25" AbsoluteLayout.LayoutFlags="All" >

        </StackLayout>

        <Grid RowSpacing="0" ColumnSpacing="0"  AbsoluteLayout.LayoutBounds="0,1,1,0.75" AbsoluteLayout.LayoutFlags="All">
            <Grid.RowDefinitions>
                <RowDefinition Height="Auto"/>
                <RowDefinition Height="*"/>
                <RowDefinition Height="*"/>
                <RowDefinition Height="*"/>
                <RowDefinition Height="*"/>
                <RowDefinition Height="*"/>
            </Grid.RowDefinitions>
            <Grid.ColumnDefinitions>
                <ColumnDefinition Width="Auto"/>
                <ColumnDefinition Width="*"/>
                <ColumnDefinition Width="*"/>
                <ColumnDefinition Width="*"/>
            </Grid.ColumnDefinitions>

            <Button Grid.Column="0" Grid.Row="0" Text="mc" />
            <Button Grid.Column="1" Grid.Row="0" Text="m+"/>
            <Button Grid.Column="2" Grid.Row="0" Text="m-"/>
            <Button Grid.Column="3" Grid.Row="0" Text="mr"/>
            <Button Grid.Column="0" Grid.Row="1" Text="C"/>
            <Button Grid.Column="1" Grid.Row="1" Text="/"/>
            <Button Grid.Column="2" Grid.Row="1" Text="X"/>
            <Button Grid.Column="3" Grid.Row="1" Text="Del"/>
            <Button Grid.Column="0" Grid.Row="2" Text="7"/>
            <Button Grid.Column="1" Grid.Row="2" Text="8"/>
            <Button Grid.Column="2" Grid.Row="2" Text="9"/>
            <Button Grid.Column="3" Grid.Row="2" Text="-"/>
            <Button Grid.Column="0" Grid.Row="3" Text="4"/>
            <Button Grid.Column="1" Grid.Row="3" Text="5"/>
            <Button Grid.Column="2" Grid.Row="3" Text="6"/>
            <Button Grid.Column="3" Grid.Row="3" Text="+"/>
            <Button Grid.Column="0" Grid.Row="4" Text="1"/>
            <Button Grid.Column="1" Grid.Row="4" Text="2"/>
            <Button Grid.Column="2" Grid.Row="4" Text="3"/>
            <Button Grid.Column="3" Grid.Row="4" Grid.RowSpan="2" Text="="/>
            <Button Grid.Column="0" Grid.Row="5" Text="%" />
            <Button Grid.Column="1" Grid.Row="5" Text="0"/>
            <Button Grid.Column="2" Grid.Row="5" Text=","/>
        </Grid>

    </AbsoluteLayout>
</ContentPage>

That I get is:

As you can see there are spaces between every row and column. Do you have any suggestions?

Do you have anything what could help me?

Body:
You could do this via custom renderer.

MyButton.cs

 public class MyButton : Button
{
}

MyButtonRenderer.cs

 [assembly: ExportRenderer(typeof(MyButton), typeof(MyButtonRenderer))]
 namespace XamarinDemo.Droid
 {
   public class MyButtonRenderer : Xamarin.Forms.Platform.Android.AppCompat.ButtonRenderer
   {

    public MyButtonRenderer(Context context) : base(context)
    {

    }

    protected override void OnElementChanged(ElementChangedEventArgs<Xamarin.Forms.Button> e)
    {
        base.OnElementChanged(e);
        if (Control != null)
        {
            Control.Background = null;
            Control.SetBackgroundColor(Android.Graphics.Color.Gray);
        }
    }

    protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
    {
        base.OnElementPropertyChanged(sender, e);
        if (e.PropertyName == "BackgroundColor")
        {
            Control.SetBackgroundColor(Android.Graphics.Color.Gray);
        }
    }
  }
}

Xaml

 <AbsoluteLayout>
    <StackLayout AbsoluteLayout.LayoutBounds="0,0,1,0.25" AbsoluteLayout.LayoutFlags="All">
        <Label x:Name="live" FontSize="20" />
        <Label x:Name="rez" FontSize="15" />
    </StackLayout>

    <Grid
        AbsoluteLayout.LayoutBounds="0,1,1,0.75"
        AbsoluteLayout.LayoutFlags="All"
        ColumnSpacing="0"
        RowSpacing="0">
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto" />
            <RowDefinition Height="*" />
            <RowDefinition Height="*" />
            <RowDefinition Height="*" />
            <RowDefinition Height="*" />
            <RowDefinition Height="*" />
        </Grid.RowDefinitions>
        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="Auto" />
            <ColumnDefinition Width="*" />
            <ColumnDefinition Width="*" />
            <ColumnDefinition Width="*" />
        </Grid.ColumnDefinitions>

        <local:MyButton
            Grid.Row="0"
            Grid.Column="0"
            Text="mc" />
        <local:MyButton
            Grid.Row="0"
            Grid.Column="1"
            Text="m+" />
        <local:MyButton
            Grid.Row="0"
            Grid.Column="2"
            Text="m-" />
        <local:MyButton
            Grid.Row="0"
            Grid.Column="3"
            Text="mr" />
        <local:MyButton
            Grid.Row="1"
            Grid.Column="0"
            Text="C" />
        <local:MyButton
            Grid.Row="1"
            Grid.Column="1"
            Text="/" />
        <local:MyButton
            Grid.Row="1"
            Grid.Column="2"
            Text="X" />
        <local:MyButton
            Grid.Row="1"
            Grid.Column="3"
            Text="Del" />
        <local:MyButton
            Grid.Row="2"
            Grid.Column="0"
            Text="7" />
        <local:MyButton
            Grid.Row="2"
            Grid.Column="1"
            Text="8" />
        <local:MyButton
            Grid.Row="2"
            Grid.Column="2"
            Text="9" />
        <local:MyButton
            Grid.Row="2"
            Grid.Column="3"
            Text="-" />
        <local:MyButton
            Grid.Row="3"
            Grid.Column="0"
            Text="4" />
        <local:MyButton
            Grid.Row="3"
            Grid.Column="1"
            Text="5" />
        <local:MyButton
            Grid.Row="3"
            Grid.Column="2"
            Text="6" />
        <local:MyButton
            Grid.Row="3"
            Grid.Column="3"
            Text="+" />
        <local:MyButton
            Grid.Row="4"
            Grid.Column="0"
            Text="1" />
        <local:MyButton
            Grid.Row="4"
            Grid.Column="1"
            Text="2" />
        <local:MyButton
            Grid.Row="4"
            Grid.Column="2"
            Text="3" />
        <local:MyButton
            Grid.Row="4"
            Grid.RowSpan="2"
            Grid.Column="3"
            Text="=" />
        <local:MyButton
            Grid.Row="5"
            Grid.Column="0"
            Text="%" />
        <local:MyButton
            Grid.Row="5"
            Grid.Column="1"
            Text="0" />
        <local:MyButton
            Grid.Row="5"
            Grid.Column="2"
            Text="," />
    </Grid>

</AbsoluteLayout>


问:
Just another dynamodb single table design question (YADSTD)

This image represents a model design to get data from a relationship between movies, actors, and directors.

From my understand from the MOV#xyz1234 partition key, they use movieId as part of the primary key to store movies, actors and directors. So for entity movie "PK = MOV#movieId and SK = MOV#movieId" this way if you want to get a movie details you can query by:

```<code>PK START_WITH MOV# AND SK = MOV#movieId
</code>```

And then to store an actor they will use "PK = MOV#movieId and SK = ACT#actorID" this way to get all actors from a movie the query could be:

```<code>PK = MOV#movieId and SK START_WITH ACT#
</code>```

Or if we want an actor details we could query as:

```<code>PK START_WITH MOV# AND SK = ACT#actorId
</code>```

But I get confuse when then I found ACT#aac1004 partition key and DIR#bce0557.
My question is: when they created a movie, they stored more than one item at the same time for each entity? How do they store actors and directors. If a movie has a lot of actors, then how to get here:

答:
The rows with MOV# as PK and ACT# establish the relationship that an actor was in a particular movie and may contain attributes about that actor's specific relationship with the movie (i.e. character name, title of movie, etc).

The rows with ACT# as the PK will contain the actor information unrelated to movies (e.g. Date of birth, Bio, etc)

One thing to note in your question is you can't query a PK with "starts with" and that is why a GSI (Global Secondary Index) is added on the SK column so you can query that directly without knowing what the PK column is.  The GSI's PK is the SK column so you can query that directly.

So to correct some of the things in your question, if you want to get movie details you would query the normal PK with:

PK = MOV#movieId AND SK = MOV#movieId

If you wanted actor details we could query:

GSI PK = ACT#actorId

And this will return the actor row (PK = ACT#actorID) with actor info as well as all of the rows where PK = MOV# where the actor is the SK.

I'm not sure if this answers the question but hopefully sheds some light on how single table designs work a little better.

Body:
This image represents a model design to get data from a relationship between movies, actors, and directors.

From my understand from the MOV#xyz1234 partition key, they use movieId as part of the primary key to store movies, actors and directors. So for entity movie "PK = MOV#movieId and SK = MOV#movieId" this way if you want to get a movie details you can query by:

PK START_WITH MOV# AND SK = MOV#movieId

And then to store an actor they will use "PK = MOV#movieId and SK = ACT#actorID" this way to get all actors from a movie the query could be:

PK = MOV#movieId and SK START_WITH ACT#

Or if we want an actor details we could query as:

PK START_WITH MOV# AND SK = ACT#actorId

But I get confuse when then I found ACT#aac1004 partition key and DIR#bce0557.
My question is: when they created a movie, they stored more than one item at the same time for each entity? How do they store actors and directors. If a movie has a lot of actors, then how to get here:


问:
RC2 Implementation differences C# and Python?
For compatibility/legacy reasons I need to use RC2 encryption in CBC mode.
I am writing a test - but I get completely different results in C#, Python and with Online Tools, with the (seemingly) same input values.

For all implementations I used the following data:

```<code>Data: 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
Key: 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
IV: 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08
Mode: CBC
Padding: PKCS7
</code>```

I tried testing this with Python, C# and by using an online tool called CyberChef.
All gave me totally different results.

Python Result: d123f2ac56146f3cebd19b285eb1e1744b828a177778be07

C# Result: f278304ee422a8bbccd54c9157afa818ac4e5b21858ff267

CyberChef Result: c91e276fc97e71acb72426f29c3a6c6f5181d8e83dcf1a98

The python scripts:

from Crypto.Cipher import ARC2
from Crypto.Util.Padding import pad
input = bytes([0]*16)
key = bytes([0]*8)
iv = b"\x01\x02\x03\x04\x05\x06\x07\x08"

cipher = ARC2.new(key, ARC2.MODE_CBC, iv=iv)

msg = cipher.encrypt(pad(input,8,style='pkcs7'))
print("{} {}".format(len(msg), msg.hex()))
```

<p>C# Script (parts):</p>

<pre class="lang-cs prettyprint-override"><code>public byte[] Encrypt(Rc2CryptoParameters cryptoParameters)
{
    using var outputStream = new MemoryStream();
    using var provider = GetRc2Provider(cryptoParameters);
    using var encryptor = provider.CreateEncryptor();
    using var cryptoStream = new CryptoStream(outputStream, encryptor, CryptoStreamMode.Write);

    cryptoStream.Write(cryptoParameters.Data);
    cryptoStream.Close();
    return outputStream.ToArray();
}

private RC2CryptoServiceProvider GetRc2Provider(Rc2CryptoParameters cryptoParameters)
{
    return new RC2CryptoServiceProvider
    {
        Key = cryptoParameters.Key,
        BlockSize = cryptoParameters.BlockSize,
        KeySize = cryptoParameters.KeySize,
        Padding = cryptoParameters.PaddingMode,
        Mode = cryptoParameters.CipherMode
    };
}

public Rc2CryptoParameters(byte[] data, byte[] key, byte[] iv)
{
    Data = data;
    Iv = iv;
    Key = key;
    CipherMode = CipherMode.CBC;
    PaddingMode = PaddingMode.PKCS7;
}
</code>```

So - why am I getting different results everywhere? I tried using some CBC testvectors, the only ones I could find were these: http://cryptomanager.com/tv.html

How can I ensure which of the results is correct?
Why are all the implementations producing different results?

答:
RC2 is described in RFC2268. It's a block cipher with variable key length and has an additional parameter called effective key length in bits, see RFC2268, Section 2. In the two codes and on the website, a different effective key length in bits is used, causing the different results.

In the Python code, when using PyCryptodome, the effective key length in bits is specified with the parameter effective_keylen upon creation of the ARC2-cipher instance, which may have values between 40 and 1024, where 1024 is the default value. Since the parameter isn't explicitly specified in the posted Python code, the default value is used. Note that this parameter is described in the PyCrypto documentation, but not in the PyCryptodome documentation.

The ciphertext of the website results for effective_keylen = 128. On the website there seems to be no possibility to change the effective key length in bits.

The ciphertext of the C# code can't be reproduced, probably because the IV isn't set in GetRc2Provider (so that the randomly generated IV is used). If this is fixed, it turns out that the effective key length in bits (RC2CryptoServiceProvider#EffectiveKeySize) is implicitly set to the actual key length. If the parameter is explicitly switched to a another value, a System.Security.Cryptography.CryptographicUnexpectedOperationException: EffectiveKeySize must be the same as KeySize in this implementation. is thrown.

Body:
For compatibility/legacy reasons I need to use RC2 encryption in CBC mode.
I am writing a test - but I get completely different results in C#, Python and with Online Tools, with the (seemingly) same input values.

For all implementations I used the following data:

Data: 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
Key: 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
IV: 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08
Mode: CBC
Padding: PKCS7

I tried testing this with Python, C# and by using an online tool called CyberChef.
All gave me totally different results.

Python Result: d123f2ac56146f3cebd19b285eb1e1744b828a177778be07

C# Result: f278304ee422a8bbccd54c9157afa818ac4e5b21858ff267

CyberChef Result: c91e276fc97e71acb72426f29c3a6c6f5181d8e83dcf1a98

The python scripts:

from Crypto.Cipher import ARC2
from Crypto.Util.Padding import pad
input = bytes([0]*16)
key = bytes([0]*8)
iv = b"\x01\x02\x03\x04\x05\x06\x07\x08"

cipher = ARC2.new(key, ARC2.MODE_CBC, iv=iv)

msg = cipher.encrypt(pad(input,8,style='pkcs7'))
print("{} {}".format(len(msg), msg.hex()))

C# Script (parts):

public byte[] Encrypt(Rc2CryptoParameters cryptoParameters)
{
    using var outputStream = new MemoryStream();
    using var provider = GetRc2Provider(cryptoParameters);
    using var encryptor = provider.CreateEncryptor();
    using var cryptoStream = new CryptoStream(outputStream, encryptor, CryptoStreamMode.Write);

    cryptoStream.Write(cryptoParameters.Data);
    cryptoStream.Close();
    return outputStream.ToArray();
}

private RC2CryptoServiceProvider GetRc2Provider(Rc2CryptoParameters cryptoParameters)
{
    return new RC2CryptoServiceProvider
    {
        Key = cryptoParameters.Key,
        BlockSize = cryptoParameters.BlockSize,
        KeySize = cryptoParameters.KeySize,
        Padding = cryptoParameters.PaddingMode,
        Mode = cryptoParameters.CipherMode
    };
}

public Rc2CryptoParameters(byte[] data, byte[] key, byte[] iv)
{
    Data = data;
    Iv = iv;
    Key = key;
    CipherMode = CipherMode.CBC;
    PaddingMode = PaddingMode.PKCS7;
}

So - why am I getting different results everywhere? I tried using some CBC testvectors, the only ones I could find were these: http://cryptomanager.com/tv.html

How can I ensure which of the results is correct?
Why are all the implementations producing different results?


问:
Vuetify.js - How to add a lateral border in a v-card
How to add a colored lateral border on only one side of a v-card component.

Example:

答:
You can target the specific Vuetify class. You can use Chrome Dev Tools to find out what class the v-card has and you can modify it using that class.

Example:

```<code>.v-content .v-card.v-sheet.theme--light {
    background-color: #ffffff !important;
    border-left: 5px solid red !important
}
</code>```

Codepen

Body:
You can target the specific Vuetify class. You can use Chrome Dev Tools to find out what class the v-card has and you can modify it using that class.

Example:

.v-content .v-card.v-sheet.theme--light {
    background-color: #ffffff !important;
    border-left: 5px solid red !important
}

Codepen


问:
How does defining a function nested in another work?
In the Python implementation of the Xiaolin Wu's line algorithm, a function is defined while being nested in another function. Part of the code:

```<code>def draw_line(img, p1, p2, color):
    """Draws an anti-aliased line in img from p1 to p2 with the given color."""
    x1, y1 = p1
    x2, y2 = p2
    dx, dy = x2-x1, y2-y1
    steep = abs(dx) < abs(dy)
    p = lambda px, py: ((px,py), (py,px))[steep]

    if steep:
        x1, y1, x2, y2, dx, dy = y1, x1, y2, x2, dy, dx
    if x2 < x1:
        x1, x2, y1, y2 = x2, x1, y2, y1

    grad = dy/dx
    intery = y1 + _rfpart(x1) * grad
    def draw_endpoint(pt):
        x, y = pt
        xend = round(x)
        yend = y + grad * (xend - x)
        xgap = _rfpart(x + 0.5)
        px, py = int(xend), int(yend)
        putpixel(img, p(px, py), color, _rfpart(yend) * xgap)
        putpixel(img, p(px, py+1), color, _fpart(yend) * xgap)
        return px
</code>```

How does this work? Why didn't the programmer just define the code somewhere else and then call it in this function? If this function where to be called in a loop to draw multiple lines, wouldn't it be more efficient to just, as I said, define the nested function somewhere else?

答:
try this:</p>

```<code>class Humans():
    def health(self, weight, height, age):
        self.weight = weight
        self.height = height
        self.age = age
    def health_health(self):
        print(f'''This human is {self.age} years old; weighs {self.weight},
        and has a height of {self.height}''')
Harar = Humans()
Harar.health(1,2,3)
Harar.health_health()
</code>```

Body:
In the Python implementation of the Xiaolin Wu's line algorithm, a function is defined while being nested in another function. Part of the code:

def draw_line(img, p1, p2, color):
    """Draws an anti-aliased line in img from p1 to p2 with the given color."""
    x1, y1 = p1
    x2, y2 = p2
    dx, dy = x2-x1, y2-y1
    steep = abs(dx) < abs(dy)
    p = lambda px, py: ((px,py), (py,px))[steep]

    if steep:
        x1, y1, x2, y2, dx, dy = y1, x1, y2, x2, dy, dx
    if x2 < x1:
        x1, x2, y1, y2 = x2, x1, y2, y1

    grad = dy/dx
    intery = y1 + _rfpart(x1) * grad
    def draw_endpoint(pt):
        x, y = pt
        xend = round(x)
        yend = y + grad * (xend - x)
        xgap = _rfpart(x + 0.5)
        px, py = int(xend), int(yend)
        putpixel(img, p(px, py), color, _rfpart(yend) * xgap)
        putpixel(img, p(px, py+1), color, _fpart(yend) * xgap)
        return px

How does this work? Why didn't the programmer just define the code somewhere else and then call it in this function? If this function where to be called in a loop to draw multiple lines, wouldn't it be more efficient to just, as I said, define the nested function somewhere else?

Body:
try this:

class Humans():
    def health(self, weight, height, age):
        self.weight = weight
        self.height = height
        self.age = age
    def health_health(self):
        print(f'''This human is {self.age} years old; weighs {self.weight},
        and has a height of {self.height}''')
Harar = Humans()
Harar.health(1,2,3)
Harar.health_health()


问:
CentOS Linux release 8.0.1905 not taking change of php.ini
I want to remove output_buffering and want to make change to memory_limit by editing etc/php.ini file

But none of my changes are taking effect.
After editing etc/php.ini file as a super user. I've restarted httpd.service using following command

```<code>sudo systemctl restart httpd.service
</code>```

I am using centOS 8

```<code>[root@backend adminuser]# cat /etc/*release
CentOS Linux release 8.0.1905 (Core)
NAME="CentOS Linux"
VERSION="8 (Core)"
ID="centos"
ID_LIKE="rhel fedora"
VERSION_ID="8"
PLATFORM_ID="platform:el8"
PRETTY_NAME="CentOS Linux 8 (Core)"
ANSI_COLOR="0;31"
CPE_NAME="cpe:/o:centos:centos:8"
HOME_URL="https://www.centos.org/"
BUG_REPORT_URL="https://bugs.centos.org/"

CENTOS_MANTISBT_PROJECT="CentOS-8"
CENTOS_MANTISBT_PROJECT_VERSION="8"
REDHAT_SUPPORT_PRODUCT="centos"
REDHAT_SUPPORT_PRODUCT_VERSION="8"

CentOS Linux release 8.0.1905 (Core)
CentOS Linux release 8.0.1905 (Core)
</code>```

php-common packages are as below

```<code>[root@backend adminuser]# rpm -qc php-common
/etc/php-zts.d/20-bz2.ini
/etc/php-zts.d/20-calendar.ini
/etc/php-zts.d/20-ctype.ini
/etc/php-zts.d/20-curl.ini
/etc/php-zts.d/20-exif.ini
/etc/php-zts.d/20-fileinfo.ini
/etc/php-zts.d/20-ftp.ini
/etc/php-zts.d/20-gettext.ini
/etc/php-zts.d/20-iconv.ini
/etc/php-zts.d/20-phar.ini
/etc/php-zts.d/20-sockets.ini
/etc/php-zts.d/20-tokenizer.ini
/etc/php.d/20-bz2.ini
/etc/php.d/20-calendar.ini
/etc/php.d/20-ctype.ini
/etc/php.d/20-curl.ini
/etc/php.d/20-exif.ini
/etc/php.d/20-fileinfo.ini
/etc/php.d/20-ftp.ini
/etc/php.d/20-gettext.ini
/etc/php.d/20-iconv.ini
/etc/php.d/20-phar.ini
/etc/php.d/20-sockets.ini
/etc/php.d/20-tokenizer.ini
/etc/php.ini
</code>```

For SSE Script I want to make output_buffer as null or Off like my another server but its not taking any change. I tested by changing php.ini as a root user and restarted httpd services.

答: You don't mention whether you're using mod_php or php-fpm. Running sudo systemctl restart httpd.service only helps for mod_php. If you're using php-fpm, you need sudo systemctl restart php-fpm.service instead.

Body:
I want to remove output_buffering and want to make change to memory_limit by editing etc/php.ini file

But none of my changes are taking effect.
After editing etc/php.ini file as a super user. I've restarted httpd.service using following command

sudo systemctl restart httpd.service

I am using centOS 8

[root@backend adminuser]# cat /etc/*release
CentOS Linux release 8.0.1905 (Core)
NAME="CentOS Linux"
VERSION="8 (Core)"
ID="centos"
ID_LIKE="rhel fedora"
VERSION_ID="8"
PLATFORM_ID="platform:el8"
PRETTY_NAME="CentOS Linux 8 (Core)"
ANSI_COLOR="0;31"
CPE_NAME="cpe:/o:centos:centos:8"
HOME_URL="https://www.centos.org/"
BUG_REPORT_URL="https://bugs.centos.org/"

CENTOS_MANTISBT_PROJECT="CentOS-8"
CENTOS_MANTISBT_PROJECT_VERSION="8"
REDHAT_SUPPORT_PRODUCT="centos"
REDHAT_SUPPORT_PRODUCT_VERSION="8"

CentOS Linux release 8.0.1905 (Core)
CentOS Linux release 8.0.1905 (Core)

php-common packages are as below

[root@backend adminuser]# rpm -qc php-common
/etc/php-zts.d/20-bz2.ini
/etc/php-zts.d/20-calendar.ini
/etc/php-zts.d/20-ctype.ini
/etc/php-zts.d/20-curl.ini
/etc/php-zts.d/20-exif.ini
/etc/php-zts.d/20-fileinfo.ini
/etc/php-zts.d/20-ftp.ini
/etc/php-zts.d/20-gettext.ini
/etc/php-zts.d/20-iconv.ini
/etc/php-zts.d/20-phar.ini
/etc/php-zts.d/20-sockets.ini
/etc/php-zts.d/20-tokenizer.ini
/etc/php.d/20-bz2.ini
/etc/php.d/20-calendar.ini
/etc/php.d/20-ctype.ini
/etc/php.d/20-curl.ini
/etc/php.d/20-exif.ini
/etc/php.d/20-fileinfo.ini
/etc/php.d/20-ftp.ini
/etc/php.d/20-gettext.ini
/etc/php.d/20-iconv.ini
/etc/php.d/20-phar.ini
/etc/php.d/20-sockets.ini
/etc/php.d/20-tokenizer.ini
/etc/php.ini

For SSE Script I want to make output_buffer as null or Off like my another server but its not taking any change. I tested by changing php.ini as a root user and restarted httpd services.


问:
aws lambda Unable to import module 'lambda_function': No module named 'requests'
I have recently started to use AWS Lambda to use triggers against some python code I have written. I currently have 2 lambda functions, both of which have been created with ZIP files. The second one I created is supposed to test the trigger events.

This is for testing purposes so I'm using the best code of all:

```<code>def lambda_handler(event, context):
    print ("Hello World")
</code>```

However, I get this error back:

```<code>Response:
{
  "errorMessage": "Unable to import module 'lambda_function'"
}

Request ID:
"65024f16-172c-11e8-ab26-27ff3322e597"

Function Logs:
START RequestId: 65024f16-172c-11e8-ab26-27ff3322e597 Version: $LATEST
Unable to import module 'lambda_function': No module named 'requests'

END RequestId: 65024f16-172c-11e8-ab26-27ff3322e597
REPORT RequestId: 65024f16-172c-11e8-ab26-27ff3322e597  Duration: 15.93 ms
Billed Duration: 100 ms     Memory Size: 128 MB Max Memory Used: 22 MB
</code>```

Everywhere I have searched for this, the answer was solved by making sure the names for the functions were correct or making sure the .zip file was readable. I have satisfied both of these conditions (the name of the file is lambda_function.py and it is in the root).

Alternatively, it seems like it might be an issue with the logs. I double checked my permission and I have the ability to create logs with all resources. Any other ideas what the issue might be?

答:
Give it a check to this answer

If you're working with Python on AWS Lambda, and need to use requests, you better use urllib3, it is currently supported on AWS Lambda and you can import it directly, check the example on urllib3 site.

import urllib3

http = urllib3.PoolManager()
r = http.request('GET', 'http://httpbin.org/robots.txt')

r.data
# b'User-agent: *\nDisallow: /deny\n'
r.status
# 200
```

Body:
I have recently started to use AWS Lambda to use triggers against some python code I have written. I currently have 2 lambda functions, both of which have been created with ZIP files. The second one I created is supposed to test the trigger events.

This is for testing purposes so I'm using the best code of all:

def lambda_handler(event, context):
    print ("Hello World")

However, I get this error back:

Response:
{
  "errorMessage": "Unable to import module 'lambda_function'"
}

Request ID:
"65024f16-172c-11e8-ab26-27ff3322e597"

Function Logs:
START RequestId: 65024f16-172c-11e8-ab26-27ff3322e597 Version: $LATEST
Unable to import module 'lambda_function': No module named 'requests'

END RequestId: 65024f16-172c-11e8-ab26-27ff3322e597
REPORT RequestId: 65024f16-172c-11e8-ab26-27ff3322e597  Duration: 15.93 ms
Billed Duration: 100 ms     Memory Size: 128 MB Max Memory Used: 22 MB

Everywhere I have searched for this, the answer was solved by making sure the names for the functions were correct or making sure the .zip file was readable. I have satisfied both of these conditions (the name of the file is lambda_function.py and it is in the root).

Alternatively, it seems like it might be an issue with the logs. I double checked my permission and I have the ability to create logs with all resources. Any other ideas what the issue might be?


问:
SQL Query Merge 2 Columns Into 1 Column By Eliminating Value
I have a data like this

I have tried to merge the columns into one column without 110, but my output is like this:

PS: Selling 7 and Selling 8 is not contains 110, I didn't want to show it

my query:

```<code>select name,
       (case when credit_code <> 110 then credit_code
             when debit_code <> 110 then debit_code
        end) as code from t;
</code>```

My expected output is like this:

How to query like my expected output?

答:
If you only want rows that have a 110 in one of the columns, use a where clause:

```<code>select name,
       (case when credit_code <> 110 then credit_code
             when debit_code <> 110 then debit_code
        end) as code
from t
where 110 in (credit_code, debit_code);
</code>```

Body:
I have a data like this

I have tried to merge the columns into one column without 110, but my output is like this:

PS: Selling 7 and Selling 8 is not contains 110, I didn't want to show it

my query:

select name,
       (case when credit_code <> 110 then credit_code
             when debit_code <> 110 then debit_code
        end) as code from t;

My expected output is like this:

How to query like my expected output?

Body:
If you only want rows that have a 110 in one of the columns, use a where clause:

select name,
       (case when credit_code <> 110 then credit_code
             when debit_code <> 110 then debit_code
        end) as code
from t
where 110 in (credit_code, debit_code);


问:
How to set non-blinking text cursor (assembly)?
My program should set non-blinking text cursor. I only have found how to hide cursor (using 10h).
Cursor should be visible but non-blinking. Is it possible?</p>

答:
The VGA uses bit 7 of the attribute byte to indicate blinking.  You can turn off this feature so that you can use bit 7 to indicate intensity.

An old note I have is now only Archive.org'ed, but I have been using some code that has worked for some time.

```<code>       ; =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
       ; make sure the 'blink' bit is off
       ; this is so we can print bright colors instead of the
       ;  vga using bit 7 as the blink bit.
       mov  dx,3DAh             ; reset the flip-flop
       in   al,dx

       mov  dx,3C0h             ; index 0x10  (20h + 10h)?
       mov  al,30h
       out  dx,al

       inc  dx                  ;  clear bit 3 to disable blink
       in   al,dx
       and  al,(~(1<<3))
       dec  dx
       out  dx,al
</code>```

Please note that this assumes there is a standard VGA, these particular registers are at 0x3DA, 0x3C0, and 0x3C1, this will be run from TRUE DOS--not a Windowed Session, along with a lot of other assumptions.

Again, this must be on a TRUE DOS machine, or at least a platform that actually is using the VGA hardware instead of emulating it.  Also, don't be surprised if modern hardware doesn't even have the VGA hardware anymore.

With all of these assumptions, as Jester stated, it would be best to hide the cursor and draw your own.

However, if you do get this to work, and it should in a standard older style machines, it allows you to use the intensity colors, i.e.: bright white, bright blue, etc.

Body:
The VGA uses bit 7 of the attribute byte to indicate blinking.  You can turn off this feature so that you can use bit 7 to indicate intensity.

An old note I have is now only Archive.org'ed, but I have been using some code that has worked for some time.

       ; =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
       ; make sure the 'blink' bit is off
       ; this is so we can print bright colors instead of the
       ;  vga using bit 7 as the blink bit.
       mov  dx,3DAh             ; reset the flip-flop
       in   al,dx

       mov  dx,3C0h             ; index 0x10  (20h + 10h)?
       mov  al,30h
       out  dx,al

       inc  dx                  ;  clear bit 3 to disable blink
       in   al,dx
       and  al,(~(1<<3))
       dec  dx
       out  dx,al

Please note that this assumes there is a standard VGA, these particular registers are at 0x3DA, 0x3C0, and 0x3C1, this will be run from TRUE DOS--not a Windowed Session, along with a lot of other assumptions.

Again, this must be on a TRUE DOS machine, or at least a platform that actually is using the VGA hardware instead of emulating it.  Also, don't be surprised if modern hardware doesn't even have the VGA hardware anymore.

With all of these assumptions, as Jester stated, it would be best to hide the cursor and draw your own.

However, if you do get this to work, and it should in a standard older style machines, it allows you to use the intensity colors, i.e.: bright white, bright blue, etc.


问:
More space between lines in TextView
I have a TextView with about 10 rows. I want to have the lines more separated from each other. I can't seem to find an attribute for doing that. I tried with: android:includeFontPadding="true" but the text got all weird like stretched or something. Is there any attribute that I don't know about to do that?

Thanks in advance.

答: Use android:lineSpacingMultiplier="1.2" or some number greater than 1</p>

Title: More space between lines in TextView


问:
Java & MySQL - Error with setBoolean() method
I'm getting the error: "Column count doesn't match value count at row 1", yet I have counted and I have the right number of columns and I feel that the error is with the setBoolean() method. I have 8 columns and you will see that I'm passing 7 arguments in my method as one of the columns is an AUTO_INCREMENTE. My coding works perfectly fine if I don't use the setBoolean method replacing it for a setString, setInt or whatever else, but not when I do it with setBoolean().

Here is my code, which I hope makes my problem clearer:

I have an automatic code in my Java that creates the Database & its respective table/s if it doesn't exist:

```<code>DB.createDB("userSecInfo");
DB.createTable("accountInfo", "userSecInfo", "("+
                                              "Username VARCHAR(40) NOT NULL, "+
                                              "Pass VARCHAR(40) NOT NULL, "+
                                              "chkPwChange BOOLEAN NOT NULL DEFAULT FALSE, "+
                                              "chkPwCntChange BOOLEAN NOT NULL DEFAULT FALSE, "+
                                              "chkPwNoExpires BOOLEAN NOT NULL DEFAULT FALSE, "+
                                              "chkPwExpires BOOLEAN NOT NULL DEFAULT FALSE, "+
                                              "expirydays INT, "+
                                              "UserID INT NOT NULL AUTO_INCREMENT, "+
                                              "PRIMARY KEY (UserID))");
</code>```

I have tried defining all the boolean variables for MySQL in different ways such as BOOL, also as BOOLEAN (as it's above) and as TINYINT & TINYINT(1); but the variable definition does not seem to be the problem.

Then the programme, once it has created the Database and the tables, it proceeds to extract the information that the user has inputted and inserts it into the Database:

```<code>DB.insertUserSecAccountInfo("userSecInfo", "accountInfo", tFUsername.getText(),
                                            String.copyValueOf(pFPassword.getPassword()), chckbxUserMustChange.isSelected(),
                                            chckbxUserCannotChange.isSelected(), chckbxPasswordNeverExpires.isSelected(),
                                            chckbxPasswordExpiresAnd.isSelected(), Integer.parseInt(tFdays.getText()));
</code>```

The insertUserSecAccountInfo method as below:

```<code>public void insertUserSecAccountInfo(String db_name,String table_name, String Username, String Pass,
             boolean chkPwChange,  boolean chkPwCntChange, boolean chkPwNoExpires,boolean chkPwExpires,
             int expirydays) throws Exception {
            try {
                openConnection("whatever","password",db_name);
                String Query ="INSERT into "+ table_name +" values(?,?,?,?,?,?,?)";
                ps = Conexion.prepareStatement(Query);
                ps.setString(1, Username);
                ps.setString(2, Pass);
                ps.setBoolean(3, chkPwChange);
                ps.setBoolean(4, chkPwCntChange);
                ps.setBoolean(5, chkPwNoExpires);
                ps.setBoolean(6, chkPwExpires);
                ps.setInt(7, expirydays);
                ps.executeUpdate();
            } catch (Exception ex) {
                JOptionPane.showMessageDialog(null, "Error saving data"));
                ex.printStackTrace();
            } finally {
                closeConnection();
            }
        }
</code>```

When I run it, it shows me the error: "Column count doesn't match value count at row 1". But then I run basically the same line directly in MySQL as below, and it inserts it perfectly fine:

```<code>insert into accountInfo(Username,Pass,chkPwChange,chkPwCntChange,chkPwNoExpires,chkPwExpires,expirydays) values ('Hola','No',true,true,true,true,56);
</code>```

So it makes me feel it's a problem with the setBoolean() method, which might not be mapping or passing correctly the boolean variables from Java to MySQL; has anyone had any similar issue? I would very much appreciate any guidance with this.

Thank you in advance.

答:
Because you did not name every column explicitly, the implicit default of all columns applies. The fact that one of them has a default value is irrelevant (and autocounting is no more and no less than the script of: "Make a sequence, now set the default value for this column to NEXTVAL(nameOfGeneratedSequence)).

This has nothing whatsoever to do with setBoolean.

As some of the commenters have said, you need to always explicitly name the columns you're setting, so: `INSERT INTO " + tableName + " (Username, Pass, etc) VALUES (?,?,... etc)".

SECURITY NOTE: Storing passwords in plain text in a database does not fit with minimal security best practices. If deployed like this and it ever leaks out, you will likely receive a hefty fine or worse (In europe via the GDPR; other jurisdictions often have similar legislation), not to mention a heck of a lot of deserved media fallout. Do not do it this way. – use bcrypt and store the hash instead.

Body:
I'm getting the error: "Column count doesn't match value count at row 1", yet I have counted and I have the right number of columns and I feel that the error is with the setBoolean() method. I have 8 columns and you will see that I'm passing 7 arguments in my method as one of the columns is an AUTO_INCREMENTE. My coding works perfectly fine if I don't use the setBoolean method replacing it for a setString, setInt or whatever else, but not when I do it with setBoolean().

Here is my code, which I hope makes my problem clearer:

I have an automatic code in my Java that creates the Database & its respective table/s if it doesn't exist:

DB.createDB("userSecInfo");
DB.createTable("accountInfo", "userSecInfo", "("+
                                              "Username VARCHAR(40) NOT NULL, "+
                                              "Pass VARCHAR(40) NOT NULL, "+
                                              "chkPwChange BOOLEAN NOT NULL DEFAULT FALSE, "+
                                              "chkPwCntChange BOOLEAN NOT NULL DEFAULT FALSE, "+
                                              "chkPwNoExpires BOOLEAN NOT NULL DEFAULT FALSE, "+
                                              "chkPwExpires BOOLEAN NOT NULL DEFAULT FALSE, "+
                                              "expirydays INT, "+
                                              "UserID INT NOT NULL AUTO_INCREMENT, "+
                                              "PRIMARY KEY (UserID))");

I have tried defining all the boolean variables for MySQL in different ways such as BOOL, also as BOOLEAN (as it's above) and as TINYINT & TINYINT(1); but the variable definition does not seem to be the problem.

Then the programme, once it has created the Database and the tables, it proceeds to extract the information that the user has inputted and inserts it into the Database:

DB.insertUserSecAccountInfo("userSecInfo", "accountInfo", tFUsername.getText(),
                                            String.copyValueOf(pFPassword.getPassword()), chckbxUserMustChange.isSelected(),
                                            chckbxUserCannotChange.isSelected(), chckbxPasswordNeverExpires.isSelected(),
                                            chckbxPasswordExpiresAnd.isSelected(), Integer.parseInt(tFdays.getText()));

The insertUserSecAccountInfo method as below:

public void insertUserSecAccountInfo(String db_name,String table_name, String Username, String Pass,
             boolean chkPwChange,  boolean chkPwCntChange, boolean chkPwNoExpires,boolean chkPwExpires,
             int expirydays) throws Exception {
            try {
                openConnection("whatever","password",db_name);
                String Query ="INSERT into "+ table_name +" values(?,?,?,?,?,?,?)";
                ps = Conexion.prepareStatement(Query);
                ps.setString(1, Username);
                ps.setString(2, Pass);
                ps.setBoolean(3, chkPwChange);
                ps.setBoolean(4, chkPwCntChange);
                ps.setBoolean(5, chkPwNoExpires);
                ps.setBoolean(6, chkPwExpires);
                ps.setInt(7, expirydays);
                ps.executeUpdate();
            } catch (Exception ex) {
                JOptionPane.showMessageDialog(null, "Error saving data"));
                ex.printStackTrace();
            } finally {
                closeConnection();
            }
        }

When I run it, it shows me the error: "Column count doesn't match value count at row 1". But then I run basically the same line directly in MySQL as below, and it inserts it perfectly fine:

insert into accountInfo(Username,Pass,chkPwChange,chkPwCntChange,chkPwNoExpires,chkPwExpires,expirydays) values ('Hola','No',true,true,true,true,56);

So it makes me feel it's a problem with the setBoolean() method, which might not be mapping or passing correctly the boolean variables from Java to MySQL; has anyone had any similar issue? I would very much appreciate any guidance with this.

Thank you in advance.


问:
How to capture text of parent element after checking text of child element
```<code>store_block_list  = '//div[@class="amlocator-store-information"]'
anc ='//div[@class="amlocator-store-information"]/parent::div'

driver.get('https://www.charlottesweb.com/where-to-buy-charlottes-web/partner-locations')
wait = WebDriverWait(driver, 30)
storeElement = wait.until(EC.visibility_of_all_elements_located((By.XPATH, store_block_list)))
full_list = []
address_list = []
for store in storeElement:
    address = driver.execute_script('return arguments[0].childNodes[2].textContent;', store).strip()
    if address not in address_list:
        address_list.append(address)
        f=driver.find_element_by_xpath(anc)
        full_list.append(f.get_attribute('data-amid'))
driver.quit()
print(full_list)
</code>```

I am going through this site and what I am trying capture text of address and append to address
_list if address not in the list and then move to data-amid and capture that, the reason I am not directly capturing the dat-amid is some of the address are not unique and I only want to capture the data-amid of unique address.

答:
To capture the data-amid you can run:

```<code>   parent = store.find_element_by_xpath('..')
   grandparent = parent.find_element_by_xpath('..')
   data_amid = grandparent.get_attribute('data-amid')
</code>```

This will return the number value

One problem with your code is that you are searching for data-amid in 'f' which is using find_element_by_xpath, this will only return the first element found. Without moving up to the grandparent node the get_attribute call will only return 'None' and if you do move up from f to the grandparent find_element_by_xpath will always stop at the first element and return '1'.

If you move up the the grandparent node using ('..') from 'store' twice and then run you can get the data-amid attribute.

Here it is in your code:

```<code>    driver.get('https://www.charlottesweb.com/where-to-buy-charlottes-web/partner-locations')
    wait = WebDriverWait(driver, 30)
    storeElement = wait.until(EC.visibility_of_all_elements_located((By.XPATH, store_block_list)))
    full_list = []
    address_list = []
    for store in storeElement:
        address = driver.execute_script('return arguments[0].childNodes[2].textContent;', store).strip()
        if address not in address_list:
            address_list.append(address)
            parent = store.find_element_by_xpath('..')
            grandparent = parent.find_element_by_xpath('..')
            print(grandparent.get_attribute('data-amid'))
            full_list.append(grandparent.get_attribute('data-amid'))
    driver.quit()
    print(full_list)
</code>```

Body:
store_block_list  = '//div[@class="amlocator-store-information"]'
anc ='//div[@class="amlocator-store-information"]/parent::div'

driver.get('https://www.charlottesweb.com/where-to-buy-charlottes-web/partner-locations')
wait = WebDriverWait(driver, 30)
storeElement = wait.until(EC.visibility_of_all_elements_located((By.XPATH, store_block_list)))
full_list = []
address_list = []
for store in storeElement:
    address = driver.execute_script('return arguments[0].childNodes[2].textContent;', store).strip()
    if address not in address_list:
        address_list.append(address)
        f=driver.find_element_by_xpath(anc)
        full_list.append(f.get_attribute('data-amid'))
driver.quit()
print(full_list)

I am going through this site and what I am trying capture text of address and append to address
_list if address not in the list and then move to data-amid and capture that, the reason I am not directly capturing the dat-amid is some of the address are not unique and I only want to capture the data-amid of unique address.

Body:
To capture the data-amid you can run:

   parent = store.find_element_by_xpath('..')
   grandparent = parent.find_element_by_xpath('..')
   data_amid = grandparent.get_attribute('data-amid')

This will return the number value

One problem with your code is that you are searching for data-amid in 'f' which is using find_element_by_xpath, this will only return the first element found. Without moving up to the grandparent node the get_attribute call will only return 'None' and if you do move up from f to the grandparent find_element_by_xpath will always stop at the first element and return '1'.

If you move up the the grandparent node using ('..') from 'store' twice and then run you can get the data-amid attribute.

Here it is in your code:

    driver.get('https://www.charlottesweb.com/where-to-buy-charlottes-web/partner-locations')
    wait = WebDriverWait(driver, 30)
    storeElement = wait.until(EC.visibility_of_all_elements_located((By.XPATH, store_block_list)))
    full_list = []
    address_list = []
    for store in storeElement:
        address = driver.execute_script('return arguments[0].childNodes[2].textContent;', store).strip()
        if address not in address_list:
            address_list.append(address)
            parent = store.find_element_by_xpath('..')
            grandparent = parent.find_element_by_xpath('..')
            print(grandparent.get_attribute('data-amid'))
            full_list.append(grandparent.get_attribute('data-amid'))
    driver.quit()
    print(full_list)


问:
Error "Your cache folder contains root-owned files, due to a bug in previous versions of npm" while "npx create-react-app example_app"
When I was trying to create a new react app using npx create-react-app example_app, I get this error

[Your cache folder contains root-owned files, due to a bug in previous
  versions of npm which has since been addressed sudo chown -R 0:0
  "/root/.npm"]

I even tried to re-install create-react-app again using npm i create-react-app, it is giving the same kind of
error.

I assume after searching about it that it is due to some permissions issue. My current user doesn't have permission to /home/shubham/.npm where shubham is my username, but I am not so sure about this.

I have tried to solve this error using chown command as

```<code>sudo chown -R <username>:<groupname> /home/shubham/.npm"
</code>```

where <username> is Shubham and <groupame> is 1000, but it is still not working.

Request people to help me out.
If you need any more information, let me know.

答:
I had the same issue and several others while trying to update my npm packages. I will be honest I do not have enough knowledge of package handlers or why this fixed my situation, but I believe my version of npm and npx were causing the issues. I had errors immediately trying to install npx, node and create-react-app with my old and out of date version of npm.

I could not run npm install npx -g without --force. Once I did that I also ran npm install npm -g --force. After this I could already tell things were different.

After npm and npx were completely overwritten, I ran npm install node -g and npm install create-react-app -g without any weird problems. I created a new react app and started it error free.

(I also ran the cache command before all of this. sudo npm cache clean --force which I am unsure if it helped).

Body:
When I was trying to create a new react app using npx create-react-app example_app, I get this error

[Your cache folder contains root-owned files, due to a bug in previous
  versions of npm which has since been addressed sudo chown -R 0:0
  "/root/.npm"]

I even tried to re-install create-react-app again using npm i create-react-app, it is giving the same kind of
error.

I assume after searching about it that it is due to some permissions issue. My current user doesn't have permission to /home/shubham/.npm where shubham is my username, but I am not so sure about this.

I have tried to solve this error using chown command as

sudo chown -R <username>:<groupname> /home/shubham/.npm"

where <username> is Shubham and <groupame> is 1000, but it is still not working.

Request people to help me out.
If you need any more information, let me know.