Primera reunión del grupo virtual de usuarios Access España

Ya está convocada la primera reunión del grupo virtual de usuarios Access España.

bandera

Únete a nosotros si Access te apasiona. Entre todos vamos a construir un grupo en el que reunirnos online para exponer temas interesantes, intercambiar código, experiencias y dudas sobre todo lo que tenga algo que ver con Access.

Gestión de turnos de trabajo con Access

En determinadas empresas, o en determinados servicios, se trabajan muchas más horas a las semana de las que puede hacer un trabajador. Servicios médicos, policía, bomberos, fundiciones, funerarias, etc. dan servicio 24 horas al día 7 días a la semana y, como no hay ningún trabajador capaz de tanto, deben hacer distintos turnos que cubran todo el servicio. También es necesario hacerlos en empresas, como centros comerciales, que sin abrir 24 horas abren más horas, o durante más días, de lo que corresponde a una jornada laboral normal.

Los turnos son distintos dependiendo del tipo de trabajo, necesidades de la empresa, etc., por ejemplo, puede resultar que, dado el tipo de trabajo, por la noche se necesito menos personal, que se cierren los domingos o que no se cierre nunca, que se tenga derecho a más o menos días de descanso, etc. Dependiendo de esas necesidades, cada empresa organiza sus turnos de una manera distinta pero los resultados tienen cosas en común: Se elabora una secuencia de los distintos turnos o tipos de jornada que debe hacer un trabajador y se organiza a los trabajadores en grupos, de manera que empezando cada uno la secuencia en una fecha distinta, se solapen unos con otros y cubran toda la jornada.

Supongamos un caso muy sencillo: Cuatro trabajadores deben cubrir mañana tarde y noche y libran un día de cada cuatro. La secuencia sería mañana, tarde, noche, libre MTNL y cada trabajador la iniciaría con un día de diferencia.

Trabajador 1: MTNLMTNLMTNLMTNLMTNL…

Trabajador 2: TNLMTNLMTNLMTNLMTNLM…

Trabajador 3: NLMTNLMTNLMTNLMTNLMT…

Trabajador 4: LMTNLMTNLMTNLMTNLMTN…

Cada columna representa un día y con este esquema se garantiza que todos los días haya un trabajador de tarde, otro de noche y otro librando.

La mayor parte de los esquemas serán más complejos que éste, pero lo normal es que todos tengan una secuencia de turnos fija comenzando en distinto momento para cada grupo de trabajadores. Tomando esas secuencias y esos grupos como punto de partida, vamos a proponer una serie de soluciones que faciliten la gestión de grupos de trabajo utilizando una aplicación hecha en Access.

Averiguar el turno para una fecha

Necesitamos saber qué turno de trabajo le corresponde a un trabajador o grupo en determinada fecha. La primera tentación puede ser recorrer un bucle partiendo desde un turno conocido, sin embargo, hay otro planteamiento que resulta familiar, pues es el del calendario, es decir, de la misma manera que ordenamos las fechas, que son números consecutivos, en 7 columnas, una para cada día de la semana, y luego podemos mediante una función saber qué día de la semana es una determinada fecha,  podemos ordenarlas en tantas columnas como tenga la secuencia.

Enero:

M

T

N

L

1

2

3

4

4

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

 

Para averiguar la columna que corresponde a un determinado item, hace años que descubrí el Mediterráneo al hacerme esta función:

 

'---------------------------------------------------------------------------------------
' Procedure : fColumna
' DateTime  : 17/10/10 15:10
' Author    : Chea
' Purpose   : Dada una relación de números consecutivos ordenados en columnas, devuelve la
'             columna que le corresponde a un determinado item
'---------------------------------------------------------------------------------------
'
Public Function fColumna(item As Long, Columnas As Long) As Long
fColumna = 1 + ((item + Columnas - 1) Mod (Columnas))
End Function

 

La función vale para resolver muchos problemas si se pueden plantear a partir de números consecutivos ordenados en columnas, pero es algo genérico que presupone que la primera columna es el número 1, lo cual, como en el ejemplo, no siempre es el caso y tenemos que considerar en qué columna se encuentra el número 1. Para eso con los turnos de trabajo he creado una función específica.

'---------------------------------------------------------------------------------------
' Procedure : fTurnoFecha
' DateTime  : 17/10/10 15:12
' Author    : Chea
' Purpose   : Dada una determinada cadencia de turnos expresada en una cadena, sCadena, en la que
'             los turnos vienen separados por comas, obtiene el turno que corresponde a una determinada
'             fecha, FechaCalculo. Es necesario conocer una fecha de referencia, PrimerDiaTurno,
'             que coincida con el primer día de la cadencia.
'             Usando una fecha fija como PrimerDiaturno,podemos pasar un parámetro opcional,
'             lDesplazamiento, para indicar cuantos días nos desplazamos del PrimerDiaturno.
'             Por ejemplo, podemos tener distintos grupos, cada uno empezando en un día
'             distinto, el primero tendrá desplazamiento 0, el segundo empezará un día más tarde, etc.
'---------------------------------------------------------------------------------------
'
Public Function fTurnoFecha(FechaCalculo As Date, sCadencia As String, PrimerDiaTurno As Date, Optional lDesplazamiento As Long) As String
Dim v As Variant
Dim lColumnas As Long
Dim lCompensacion As Long

v = Split(sCadencia, ",")
lColumnas = 1 + UBound(v)

lCompensacion = fColumna(Int(PrimerDiaTurno + lDesplazamiento), lColumnas) - 1
fTurnoFecha = v(fColumna(Int(FechaCalculo) - lCompensacion, lColumnas) - 1)
 
End Function

 

A la función le pasamos FechaCalculo, que es la fecha para la que queremos obtener el turno, sCadencia, que es una cadena en la que indicamos la secuencia del turno, con los items separados por comas, por ejemplo “M,T,N,L” o “Mañana,Tarde,Noche,Libre”. También le pasamos PrimerDiaTurno que es una fecha de la que sepamos con certeza que se corresponde con el primer día de la secuencia o, de manera opcional, lDesplazamiento, que podemos utilizar para indicar cuantos días se desplaza de una fecha fija, por ejemplo 0, el primer día del turno, calculándolo por tanteo.

Por ejemplo, el día en que, tras una ardua negociación de empresa y trabajadores, se elaboraron las planillas, se comprobó que el trabajador 2 debía iniciar su secuencia el 4 de enero del 2007 y se anotó esta fecha para posteriores cálculos, según esto, para cálcular cómo le toca la Nochebuena del 2010, el cálculo en la ventana de inmediato sería:

 

? fTurnoFecha (#2010/12/24#,"Mañana,Tarde,Noche,Libre",#2007/01/04#)

Noche

Aparte de para hacerle la puñeta al trabajador 2, la función se puede utilizar en una consulta para obtener una relación de todos los turnos de todos los trabajadores para todos los días de un periodo determinado.

 

Elaborar un calendario con turnos

Tomemos una tabla de empleados, con indicación de a qué grupo pertenecen


EmpleadosTurnos
Id Empleado Grupo
1 Pedro 1
2 Andrés 1
3 Jaime 1
4 Juan 2
5 Felipe 2
6 Bartolomé 2
7 Tomás 3
8 Mateo 3
9 Santiago 3
10 Judas 4
11 Simón 4
13 Matías 4

Aunque el último ID sea 13, se trata de 12 empleados, pues despidieron a uno por conducta desleal. Están organizados en 4 grupos cada uno de los cuales se inicia al día siguiente del grupo anterior. Vamos a crear el calendario correspondiente a octubre del 2010 utilizando una consulta.

Sabemos que si disponemos de una tabla Numeros poblada de numeros consecutivos empezando por el 1, podemos obtener una secuencia de fechas a base de sumar una FechaInicial menos uno al campo Numero. Este truco y el de no relacionar tablas para que el resultado sea un producto cartesiano lo vamos a utilizar en la siguiente consulta.

 

 

image

 

El texto SQL es el siguiente:

 

SELECT EmpleadosTurnos.Empleado, [Numero]+CDate("01-10-10")-1 AS FechaVirtual, EmpleadosTurnos.Grupo, fturnofecha([fechavirtual],"Mañana,Tarde,Noche, Libre",CDate("04-01-07"),[Grupo]-1) AS Turno
FROM Numeros, EmpleadosTurnos
WHERE ((([Numero]+CDate("01-10-10")-1)<=CVDate("31-10-10")))
ORDER BY EmpleadosTurnos.Empleado, [Numero]+CDate("01-10-10")-1;

Y el resultado, resumiendo, porque serían 372 filas, mostraría algo parecido a lo siguiente completado hasta mostrar todos los empleados con todas las fechas de octubre del 2010 y el turno de cada fecha

 


qTurnosVirtuales
Empleado FechaVirtual Grupo Turno
Andrés 01/10/10 1 Noche
Andrés 02/10/10 1 Libre
Andrés 03/10/10 1 Mañana
Andrés 04/10/10 1 Tarde
Andrés 05/10/10 1 Noche
Andrés 06/10/10 1 Libre
Andrés 07/10/10 1 Mañana
Andrés 08/10/10 1 Tarde
Andrés 09/10/10 1 Noche
Andrés 10/10/10 1 Libre
Andrés 27/10/10 1 Mañana
Andrés 28/10/10 1 Tarde
Andrés 29/10/10 1 Noche
Andrés 30/10/10 1 Libre
Andrés 31/10/10 1 Mañana
Bartolomé 01/10/10 2 Tarde
Bartolomé 02/10/10 2 Noche
Bartolomé 03/10/10 2 Libre
Bartolomé 04/10/10 2 Mañana
Bartolomé 05/10/10 2 Tarde
Bartolomé 06/10/10 2 Noche
Bartolomé 07/10/10 2 Libre
..

 

La consulta la podemos personalizar para pasarle las fechas inicial y final del periodo como parámetros y también podemos tomarla como puento de partida para una consulta de datos anexado o de actualización que para cada día del año y cada empleado deje anotado el turno de trabajo. Aunque no es necesario volcar los datos en una tabla, pues podemos utilizar la consulta con cualquier periodo de fechas, si resulta muy conveniente, pues además de los distintos turnos pueden darse otras situaciones, como bajas, vacaciones, cambios de turno que hacen necesario trabajar con datos guardados.

A menudo se pretende realizar una planilla que refleje los trabajadores que entran en cada turno cada día, utilizando los días como encabezado de columna.

 

 


qTurnosVirtuales_Tabla de referencias cruzadas
Empleado Grupo 01/10/10 02/10/10 25/10/10 26/10/10 27/10/10 28/10/10 29/10/10 30/10/10 31/10/10
Andrés 1 Noche Libre Noche Libre Mañana Tarde Noche Libre Mañana
Jaime 1 Noche Libre Noche Libre Mañana Tarde Noche Libre Mañana
Pedro 1 Noche Libre Noche Libre Mañana Tarde Noche Libre Mañana
Bartolomé 2 Tarde Noche Tarde Noche Libre Mañana Tarde Noche Libre
Felipe 2 Tarde Noche Tarde Noche Libre Mañana Tarde Noche Libre
Juan 2 Tarde Noche Tarde Noche Libre Mañana Tarde Noche Libre
Mateo 3 Mañana Tarde Mañana Tarde Noche Libre Mañana Tarde Noche
Santiago 3 Mañana Tarde Mañana Tarde Noche Libre Mañana Tarde Noche
Tomás 3 Mañana Tarde Mañana Tarde Noche Libre Mañana Tarde Noche
Judas 4 Libre Mañana Libre Mañana Tarde Noche Libre Mañana Tarde
Matías 4 Libre Mañana Libre Mañana Tarde Noche Libre Mañana Tarde
Simón 4 Libre Mañana Libre Mañana Tarde Noche Libre Mañana Tarde

 

Evidentemente es fácil de hacer con una consulta de referencias cruzadas.

 

image

 

El texto SQL sería:

TRANSFORM First(qTurnosVirtuales.Turno) AS PrimeroDeTurno
SELECT qTurnosVirtuales.Empleado, qTurnosVirtuales.Grupo
FROM qTurnosVirtuales
GROUP BY qTurnosVirtuales.Empleado, qTurnosVirtuales.Grupo
ORDER BY qTurnosVirtuales.Grupo
PIVOT qTurnosVirtuales.FechaVirtual;

 

Si nuestra consulta de referencias cruzadas la convertimos en un informe y usamos formato condicional, el resultado es la mar de vistoso (o la mar de hortera, según gustos). En el ejemplo le hemos quitado columnas para que nos quepa bien en la página.

image

 

En fin, se trata de una serie de ideas que pueden servir a alguien que debe plantearse la gestión de turnos de trabajo, pero no pretende ser ni “la solución” ni la forma canónica de plantearlo.

Hola a Office 365, adiós a Office Live Small Business

Al tiempo que se anunciaba el lanzamiento de la beta de Office 365, el Access Team Blog anunciaba que Office 365 incluirá Access Services y, por tanto, Access web Databases y en la comunidad online de Office Live Small Business (OLSB) daban la noticia de que, ante la llegada de Office 365, OLSB desaperecerá en el plazo de un año.

Habrá un periodo de transición para migrar de OLSB a Office 365 para pequeñas empresas a finales del 2011 o principios del siguiente, con un periodo gratuito de tres meses, pero después habrá que pagar por el servicio. Hay quien dice que a Manolete le mató el toro porque la corrida era de beneficencia y eso mismo ha debido pensar Microsoft. Para quienes migren desde OLSB, el precio parece que no será muy caro, unos 6$ al mes por cuenta, muy poco para una empresa incluso pequeña, pero bastante para sustituir a algo que se prometió como gratis de por vida (claro, de la vida del producto que ahora eliminan Triste).

Para quienes queremos jugar con las posibilidades de las aplicaciones web de Access 2010 o utilizar Sharepoint como back end de nuestras aplicaciones Access de escritorio, el anuncio es realmente prometedor pues el rendimiento Access Services es muy superior al de las listas vinculadas en Sharepoint 2007, por el volumen de datos que es capaz de gestionar sin problemas y por la velocidad notablemente superior y porque, sencillamente, las aplicaciones web de Access 2010 son impensables en Sharepoint 2007. Hasta ahora, lo más barato con Access Services era AccessHosting a partir de 19$ mes el pack developer, por lo que el precio de Office 365 para pequeñas empresas resulta muy competitivo, menos de un tercio, y eso sin contar con que los Access Services son la parte más pequeña del paquete de Office 365, que incluye Office Professional, Exchange Online, Sharepoint Online y Lync Online.

Para quienes hemos utilizado OLSB precisamente porque era un recurso gratuito de por vida, no deja de ser una faena. Algunas aplicaciones de escritorio en Access 2007 podían compartir unos pocos datos en la web de forma muy sencilla y sin coste alojándolos en OLSB. Algunos nos hemos entretenido en diseñar en OLSB páginas web sencillas para otros que no se pueden permitir un coste superior a gratis, el pequeño negocio del amigo que empieza, una actividad del colegio, etc., precisamente porque OLSB ofrecía un alojamiento gratuito con una calidad aceptable. Unos y otros, en ambos casos yo, ahora se ven decepcionados, pues no necesitaban nada más y ahora se lo quitan, ofreciéndoles a cambio, de pago, lo que no han pedido.

Así que mi entusiasmo por lo uno frena mi decepción por lo otro y viceversa y, de momento, ando más bien perplejo.

Tengo muy claro que contrataré Office 365 para la pequeña empresa por utilizar los Access Services y para seguir alojando mi página, pero para aquellas cosas en las que utilizaba OLSB por ser gratuito, empezaré a irme pasando a Google Sites ¿Habrá valorado Microsoft que esta última decisión será la lógica para miles de usuarios de OLSB?